# Source code for rstt.slbminterface

    """This file contains the `rstt.SlbmInterface` class, which interfaces with the
    raw `SlbmInterface` class exposed through `libslbmPyshell`."""

    ################################################################################
    #
    #  Copyright 2009 National Technology & Engineering Solutions of Sandia, LLC
    #  (NTESS). Under the terms of Contract DE-NA0003525 with NTESS, the U.S.
    #  Government retains certain rights in this software.
    #
    #  BSD Open Source License
    #  All rights reserved.
    #
    #  Redistribution and use in source and binary forms, with or without
    #  modification, are permitted provided that the following conditions are met:
    #
    #    1. Redistributions of source code must retain the above copyright notice,
    #       this list of conditions and the following disclaimer.
    #
    #    2. Redistributions in binary form must reproduce the above copyright
    #       notice, this list of conditions and the following disclaimer in the
    #       documentation and/or other materials provided with the distribution.
    #
    #    3. Neither the name of the copyright holder nor the names of its
    #       contributors may be used to endorse or promote products derived from
    #       this software without specific prior written permission.
    #
    #  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
    #  AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
    #  IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
    #  ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
    #  LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
    #  CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
    #  SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
    #  INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
    #  CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
    #  ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
    #  POSSIBILITY OF SUCH DAMAGE.
    #
    ################################################################################

    #-----------------------------------------
    # initialization
    #-----------------------------------------

    # everything that will be imported when we invoke `from .slbminterface import *`
    __all__ = ["SlbmInterface"]

    # import statements
    from . import libslbmPyshell  # libslbmPyshell, imported from __init__.py
    import os                     # check if files exist
    from typing import Tuple      # type hinting (purely for code documentation)

    #-----------------------------------------
    # SlbmInterface class
    #-----------------------------------------

    class SlbmInterface(libslbmPyshell.SlbmInterface):
        """:class:`SlbmInterface` is the primary interface to the RSTT C++ library.

        :class:`SlbmInterface` is the primary interface to the RSTT C++ library,
        providing access to all supported functionality. It maintains a
        cpp:class:`Grid` object which is loaded into memory with the
        :meth:`~SlbmInterface.loadVelocityModel` method. This `Grid` object
        remains in memory until the :class:`SlbmInterface` destructor is called.

        :class:`SlbmInterface` also maintains a single instance of a `GreatCircle`
        object which is instantiated with a call to :meth:`~SlbmInterface.createGreatCircle`.
        Once instantiated, many methods can retrieve information from it, such as
        :meth:`~SlbmInterface.getTravelTime`, :meth:`~SlbmInterface.getTravelTimeComponents`,
        :meth:`~SlbmInterface.getWeights`, and more. The `GreatCircle` can be
        interrogated until it is replaced with another `GreatCircle` by a subsequent
        call to :meth:`~SlbmInterface.createGreatCircle`, or it is deleted by
        :meth:`~SlbmInterface.clear`.

        Examples
        --------
        >>> slbm = SlbmInterface()

        >>> slbm = SlbmInterface(6371.)

        Notes
        -----
            By default `earth_radius` is not set, and :class:`SlbmInterface` uses the
            values from the model file.

        Parameters
        ----------
        earth_radius : float, optional
            Constant radius of the Earth in kilometers

        Attributes
        ----------
        srcLat : float
            Source latitude (radians) passed to :meth:`~SlbmInterface.createGreatCircle`
            the last time it was called
        srcLon : float
            Source longitude (radians) passed to :meth:`~SlbmInterface.createGreatCircle`
            the last time it was called
        srcDep : float
            Source depth (km) passed to :meth:`~SlbmInterface.createGreatCircle`
            the last time it was called
        rcvLat : float
            Receiver latitude (radians) passed to :meth:`~SlbmInterface.createGreatCircle`
            the last time it was called
        rcvLon : float
            Receiver longitude (radians) passed to :meth:`~SlbmInterface.createGreatCircle`
            the last time it was called
        rcvDep : float
            Receiver depth (km) passed to :meth:`~SlbmInterface.createGreatCircle`
            the last time it was called
        valid : bool
            True if the current `GreatCircle` object has been instantiated and is
            ready to be interrogated.
        CH_MAX : float
            `c` is the Zhao `c` parameter, and `h` is the turning depth of the ray
            below the Moho. The Zhao method only valid for :math:`c*h << 1`.
            When :math:`c*h > CH_MAX`, then RSTT will throw an Exception.
        """

        def __init__(self, earth_radius: float = None) -> None:
            """Constructor for the :class:`SlbmInterface` class.

            Constructor for the :class:`SlbmInterface` class. You can provide an
            Earth radius (km), if you choose, but by default the tessellation of
            the Earth is read from the RSTT model.

            Examples
            --------
            >>> slbm = SlbmInterface()

            >>> slbm = SlbmInterface(6371.)

            Notes
            -----
                By default `earth_radius` is not set, and :class:`SlbmInterface`
                uses the values from the model file.

            Parameters
            ----------
            earth_radius : float, optional
                Constant radius of the Earth in kilometers

            Raises
            ------
            ValueError
                `earth_radius` is not an `int` or `float`, or more than 1 argument
                was given
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: earth_radius is an int or float
            if earth_radius is not None:
                if not isinstance(earth_radius, (int, float)):
                    raise TypeError("earth_radius expects type 'int' or 'float', received '{}'".format(type(earth_radius).__name__))

            # try and construct the object
            try:
                if earth_radius:
                    super().__init__(earth_radius)
                else:
                    super().__init__()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def __eq__(self, other: object) -> bool:
            """Compares the model and/or great circle loaded into this and another
            SlbmInteface.

            This is an overloaded == operator which tests whether the model and/or
            great circle loaded by the current instantiation of SlbmInterface is
            equal to that of another SlbmInterface.

            Examples
            --------
            >>> slbm1 = SlbmInterface()
            >>> slbm2 = SlbmInterface()
            >>> slbm1.loadVelocityModel("example.geotess")
            >>> slbm2.loadVelocityModel("example.geotess")
            >>> slbm1 == slbm2
            True
            >>> slbm1.createGreatCircle("Pn", ...)
            >>> slbm2.createGreatCircle("Pg", ...)
            >>> slbm1 == slbm2
            False

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            """

            # if they're the same type, call the overloaded operator
            if type(self) == type(other):
                return super().__eq__(other)

            # if they're not the same type, they're definitely not equal
            else:
                return False

        def __ne__(self, other: object) -> bool:
            """This is simply the logical NOT complement to operator ==.

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            """

            # if they're the same type, call the overloaded operator
            if type(self) == type(other):
                return super().__ne__(other)

            # if they're not the same type, they're definitely not equal
            else:
                return True

        # PyBind11 does a good job dealing with the getters and setters for properties,
        # so there's no need to bother re-implementing them in here. It already works
        # well with rstt.SlbmInterface inheriting libslbmPyshell.SlbmInterface.

        # PyBind11 also deals with the SlbmInterface destructor.

        def getVersion(self) -> str:
            """Returns the RSTT version number.

            Examples
            --------
                >>> slbm.getVersion()

            Returns
            -------
            str
                The RSTT version number

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getVersion()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def clear(self) -> None:
            """Delete the current `GreatCircle` object from memory and clear the
            pool of stored `CrustalProfile` objects.

            The `Grid` object owned by :class:`SlbmInterface` stores a vector of map
            objects which associates the `phase` and `Location` of a
            `CrustalProfile` object with a pointer to the instance of the
            `CrustalProfile`. When :meth:`~SlbmInterface.createGreatCircle` is
            called with a `latitude`, `longitude`, and `depth` which has been used
            before, the `Grid` object will return a pointer to the existing
            `CrustalProfile` object, thereby enhancing performance. This vector of
            maps is cleared when :meth:`~SlbmInterface.clear` is called. The
            implications of all this is that applications that loop over many calls
            to :meth:`~SlbmInterface.createGreatCircle` will see a performance
            improvement if :meth:`~SlbmInterface.clear` is not called within the
            loop. However, for problems with a huge number of sources and or
            receivers, if memory becomes an issue, applications could call
            :meth:`~SlbmInterface.clear` within the loop to save memory.

            Examples
            --------
                >>> slbm.clear()

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().clear()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def clearActiveNodes(self) -> None:
            """Clear all active nodes.

            Examples
            --------
                >>> slbm.clearActiveNodes()

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().clearActiveNodes()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def clearNodeHitCount(self) -> None:
            """Clear the node hit count by setting the hit count of every node to zero.

            Examples
            --------
                >>> slbm.clearNodeHitCount()

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().clearNodeHitCount()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def createGreatCircle(self, phase: str or int,
                srcLatRad: float, srcLonRad: float, srcDepKm: float,
                rcvLatRad: float, rcvLonRad: float, rcvDepKm: float) -> None:
            """Instantiate a new `GreatCircle` between two locations.

            Instantiate a new `GreatCircle` objecr between a source and a receiver.
            Source and receiver locations are given in latitude/longitude with units
            of radians. Depths are given in kilometers. The `phase` can be given
            either as a string or an integer. Accepted values are:

                * `Pn` or `0`
                * `Sn` or `1`
                * `Pg` or `2`
                * `Lg` or `3`

            Examples
            --------
                >>> slbm.createGreatCircle("Lg", srcLatRad, srcLonRad, srcDepKm, rcvLatRad, rcvLonRad, rcvDepKm)
                >>> slbm.createGreatCircle(3, srcLatRad, srcLonRad, srcDepKm, rcvLatRad, rcvLonRad, rcvDepKm)

            Parameters
            ----------
            phase : str or int
                A phase name, or associated number. Accepted values are
                    * `Pn` or `0`
                    * `Sn` or `1`
                    * `Pg` or `2`
                    * `Lg` or `3`
            srcLatRad : float
                Source latitude, in radians
            srcLonRad : float
                Source longitude, in radians
            srcDepKm : float
                Source depth, in kilometers
            rcvLatRad : float
                Receiver latitude, in radians
            rcvLonRad : float
                Receiver longitude, in radians
            rcvDepKm : float
                Receiver depth, in kilometers

            Raises
            ------
            TypeError
                `phase` isn't an `int` or a `str`, or source/receiver locations
                aren't all `float`
            ValueError
                An inappropriate `phase` was supplied
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: phase is an int or str
            if not isinstance(phase, (int, str)):  # phase is an int or string
                raise TypeError("`phase` expects type 'int' or 'str', received '{}'".format(type(phase).__name__))

            # ARG CHECK: str phase is one of [Pn, Sn, Pg, Lg]
            if isinstance(phase, str):
                if phase.lower() not in ('pn', 'sn', 'pg', 'lg'):
                    raise ValueError("`phase` must be one of: 'Pn', 'Sn', 'Pg', or 'Lg'")

            # ARG CHECK: int phase is one of [0, 1, 2, 3]
            if isinstance(phase, int):
                if phase not in (0, 1, 2, 3):
                    raise ValueError("`phase` must be one of: 0 (Pn), 1 (Sn), 2 (Pg), or 3 (Lg)")

            # ARG CHECK: source/receiver locations are all floats
            if not all(isinstance(arg, float) for arg in (srcLatRad, srcLonRad, srcDepKm, rcvLatRad, rcvLonRad, rcvDepKm)):
                raise TypeError("Source/receiver locations should all be type 'float'")

            # try and call the function
            try:
                super().createGreatCircle(phase, srcLatRad, srcLonRad, srcDepKm, rcvLatRad, rcvLonRad, rcvDepKm)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getActiveNodeData(self, nodeId: int) -> Tuple[float, float,
                Tuple[float,...], Tuple[float,...], Tuple[float,...], Tuple[float,...]]:
            """Retrieve information associated with a specified active node in the
            velocity grid.

            Retrieve the latitude, longitude, interface depths, P and S wave
            interval velocities and P and S mantle gradient information associated
            with a specified active node in the velocity grid.

            Examples
            --------
                >>> slbm.getActiveNodeData(1001)

            Parameters
            ----------
            nodeId : int
                Active node in the grid

            Returns
            -------
            latitude : float
                Latitude of the active node, in radians
            longitude : float
                Longitude of the active node, in radians
            depth : tuple of floats
                Depths of all the model interfaces, in kilometers
            pvelocity : tuple of floats
                P velocities of the intervals at the active node, in kilometers per second
            svelocity : tuple of floats
                S velocities of the intervals at the active node, in kilometers per second
            gradient : tuple of floats
                P and S velocity gradients in the mantle, in 1/second

            Raises
            ------
            TypeError
                `nodeId` isn't an `int`
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: nodeId is an int
            if not isinstance(nodeId, int):  # phase is an int or string
                raise TypeError("`nodeId` expects type 'int', received '{}'".format(type(nodeId).__name__))

            # try and call the function
            try:
                return super().getActiveNodeData(nodeId)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getActiveNodeId(self, nodeId: int) -> int:
            """Retrieve the active node ID that corresponds to a specified grid node ID.

            Examples
            --------
                >>> slbm.getActiveNodeId(1001)

            Parameters
            ----------
            nodeId : int
                Node in the grid

            Returns
            -------
            int
                Active node ID

            Raises
            ------
            TypeError
                `nodeId` isn't an `int`
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: nodeId is an int
            if not isinstance(nodeId, int):  # phase is an int or string
                raise TypeError("`nodeId` expects type 'int', received '{}'".format(type(nodeId).__name__))

            # try and call the function
            try:
                return super().getActiveNodeId(nodeId)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getActiveNodeNeighborInfo(self, nodeId: int) -> Tuple[Tuple[int,...], Tuple[float,...], Tuple[float,...]]:
            """Retrieve information about the nodes that surround the specified
            active node.

            Examples
            --------
                >>> slbm.getActiveNodeNeighborInfo(11)

            Parameters
            ----------
            nodeId : int
                Active node in the grid

            Returns
            -------
            tuple of ints
                Active node neighbors of the specified active node
            tuple of floats
                Distance of active node neighbors relative to specified active node
            tuple of floats
                Azimuth of active node neighbors relative to specified active node

            Raises
            ------
            TypeError
                `nodeId` isn't an `int`
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: nodeId is an int
            if not isinstance(nodeId, int):  # phase is an int or string
                raise TypeError("`nodeId` expects type 'int', received '{}'".format(type(nodeId).__name__))

            # try and call the function
            try:
                return super().getActiveNodeNeighborInfo(nodeId)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getActiveNodeNeighbors(self, nodeId: int) -> Tuple[int, ...]:
            """Retrieve the active node IDs of the active nodes that surround the
            specified active node.

            Examples
            --------
                >>> slbm.getActiveNodeNeighbors(11)

            Parameters
            ----------
            nodeId : int
                Active node in the grid

            Returns
            -------
            tuple of ints
                Active node IDs of the active nodes that surround the specified
                active node

            Raises
            ------
            TypeError
                `nodeId` isn't an `int`
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: nodeId is an int
            if not isinstance(nodeId, int):  # phase is an int or string
                raise TypeError("`nodeId` expects type 'int', received '{}'".format(type(nodeId).__name__))

            # try and call the function
            try:
                return super().getActiveNodeNeighbors(nodeId)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getActiveNodeWeights(self) -> Tuple[Tuple[int, ...], Tuple[float, ...]]:
            """Retrieve the weight assigned to each active node that was touched by
            the `GreatCircle`.

            Only nodes touched by this `GreatCircle` are included in the output.
            Each grid node is included only once, even though more than one
            `LayerProfile` object may have contributed some weight to it. The sum of
            all the weights will equal the horizontal distance traveled by the ray
            along the head wave interface, from the source pierce point to the
            receiver pierce point, in kilometers.

            Examples
            --------
                >>> slbm.getActiveNodeWeights()

            Returns
            -------
            tuple of ints
                Active node IDs touched by this `GreatCircle`
            tuple of floats
                Weights of the touched active nodes, in kilometers

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getActiveNodeWeights()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getActiveNodeWeightsReceiver(self) -> Tuple[Tuple[int, ...], Tuple[float, ...]]:
            """Retrieve the weight assigned to each active node for the receiver
            `CrustalProfile`.

             For linear interpolation, the returned number of weights will equal 3,
             but for natural neighbor interpolation it will be variable and less
             than 10.

            Examples
            --------
                >>> slbm.getActiveNodeWeightsReceiver()

            Returns
            -------
            tuple of ints
                Active node IDs for the receiver `CrustalProfile`
            tuple of floats
                Weights of the active nodes, in kilometers

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getActiveNodeWeightsReceiver()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getActiveNodeWeightsSource(self) -> Tuple[Tuple[int, ...], Tuple[float, ...]]:
            """Retrieve the weight assigned to each active node for the source
            `CrustalProfile`.

             For linear interpolation, the returned number of weights will equal 3,
             but for natural neighbor interpolation it will be variable and less
             than 10.

            Examples
            --------
                >>> slbm.getActiveNodeWeightsReceiver()

            Returns
            -------
            tuple of ints
                Active node IDs for the source `CrustalProfile`
            tuple of floats
                Weights of the active nodes, in kilometers

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getActiveNodeWeightsSource()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getAverageMantleVelocity(self, waveType: int or str) -> float:
            """Retrieve the average P or S wave mantle velocity that is specified in
            the model input file.

            Examples
            --------
                >>> slbm.getAverageMantleVelocity('P')

            Parameters
            ----------
            waveType : str or int
                Seismic wave type. Accepted values are
                    * :attr:`~rstt.PWAVE`, `P`, or `0`
                    * :attr:`~rstt.SWAVE`, `S`, or `1`

            Returns
            -------
            float
                Average mantle velocity, in kilometers per second

            Raises
            ------
            TypeError
                `waveType` isn't an `int` or a `str`
            ValueError
                An inappropriate `waveType` was supplied
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: waveType is and int or str
            if not isinstance(waveType, (int, str)):  # waveType is an int or string
                raise TypeError("`waveType` expects type 'int' or 'str', received '{}'".format(type(waveType).__name__))

            # ARG CHECK: str waveType is one of [P, S]
            if isinstance(waveType, str):
                if waveType.lower() not in ('p', 's'):
                    raise ValueError("`waveType` must be either 'P' or 'S'")

            # ARG CHECK: int waveType is one of [0, 1]
            if isinstance(waveType, int):
                if waveType not in (0, 1):
                    raise ValueError("`waveType` must be 0 (P) or 1 (S)")

            # convert string waveType to int
            if isinstance(waveType, str):
                waveType = PWAVE if waveType.lower() == 'p' else SWAVE

            # try and call the function
            try:
                return super().getAverageMantleVelocity(waveType)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getBufferSize(self) -> int:
            """Returns the size of a `DataBuffer` object required to store this
            :class:`SlbmInterface` object's model data.

            Examples
            --------
                >>> slbm.getBufferSize()

            Returns
            -------
            int
                Size required to store this :class:`SlbmInterface` object's model
                data, in bytes

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getBufferSize()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getCHMax(self) -> float:
            """Retrieve the current value of CH_MAX.

            This call retrieves global parameter :attr:`~SlbmInterface.CH_MAX`.
            Alternatively, this parameter may be retrieved by calling it as an
            attribute of the current :class:`SlbmInterface` object.

            `c` is the Zhao `c` parameter, and `h` is the turning depth of the ray
            below the Moho. The Zhao method only valid for `c*h << 1`. When `c*h >
            CH_MAX`, then RSTT will throw an exception.

            Examples
            --------
                >>> slbm.getCHMax()

                >>> slbm.CH_MAX

            Returns
            -------
            float
                Global :attr:`~SlbmInterface.CH_MAX` parameter

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getCHMax()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getClassCount(self) -> str:
            """Retrieve a table that lists the number of instances of various RSTT
            classes that are currently instantiated.

            Very useful for debugging memory leaks.

            Examples
            --------
                >>> slbm.getClassCount()

            Returns
            -------
            str
                Table that lists the number of currently-initiated classes

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getClassCount()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getDelDepth(self) -> float:
            """Retrieve the value of step change in depth used to compute depth
            derivatives

            Examples
            --------
                >>> slbm.getDelDepth()

            Returns
            -------
            float
                Del depth, in kilometers

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getDelDepth()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getDelDistance(self) -> float:
            """Retrieve the value of step change in distance used to compute
            horizontal derivatives

            Examples
            --------
                >>> slbm.getDelDistance()

            Returns
            -------
            float
                Del distance, in radians

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getDelDistance()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getDistAz(self,
                lat1Rad: float, lon1Rad: float,
                lat2Rad: float, lon2Rad: float) -> Tuple[float, float]:
            """Compute distance and azimuth between two points.

            Computed distance will range between 0 and pi, and azimuth will range
            from -pi to pi.

            Examples
            --------
                >>> slbm.getDistAz(0.1, 0., 0.082, 0.)

            Parameters
            ----------
            lat1Rad : float
                Latitude of starting location, in radians
            lon1Rad : float
                Longitude of starting location, in radians
            lat2Rad : float
                Latitude of ending location, in radians
            lon2Rad : float
                Longitude of ending location, in radians

            Returns
            -------
            distance : float
                Distance between the two specified locations, in radians
            azimuth : float
                Azimuth between the two specified locations, in radians

            Raises
            ------
            TypeError
                Specified Lat/lon locations aren't all `float`
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: locations are all floats
            if not all(isinstance(arg, float) for arg in (lat1Rad, lon1Rad, lat2Rad, lon2Rad)):
                raise TypeError("Location latitude/longitudes should all be type 'float'")

            # try and call the function
            try:
                return super().getDistAz(lat1Rad, lon1Rad, lat2Rad, lon2Rad)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getDistance(self) -> float:
            """Retrieve the source-receiver separation.

            Examples
            --------
                >>> slbm.getDistance()

            Returns
            -------
            float
                The Source-receiver separation, in radians

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getDistance()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getFractionActive(self) -> float:
            """Retrieve the fraction of the path length of the current `GreatCircle`
            object that is within the currently-defined active region.

            Examples
            --------
                >>> slbm.getFractionActive()

            Returns
            -------
            float
                Fraction of path length in active region

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getFractionActive()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getGreatCircleData(self) -> Tuple[str, float,
                Tuple[float, ...], Tuple[float, ...],
                Tuple[float, ...], Tuple[float, ...],
                int, Tuple[float, ...], Tuple[float, ...]]:
            """Retrieve information about the great circle path.

            Retrieve information about the great circle path including the interface
            depths at source and receiver, the velocity profiles at the source and
            receiver, and mantle velocity and velocity gradient at points along the
            great circle path from source pierce point to receiver pierce point.

            The first horizontal segment starts at the source, the last horizontal
            segment ends at the receiver, and each one is of size
            `actual_path_increment`. The head wave velocities are interpolated at
            the center of each of these horizontal segments, just below the head
            wave interface.

            Examples
            --------
                >>> slbm.getGreatCircleData()

            Returns
            -------
            phase : str
                The phase supported by the current `GreatCircle`
            actual_path_increment : float
                Horizontal separation of the `LayerProfile` objects along the head
                wave interface, in radians
            sourceDepth : tuple of floats
                Depths of all the model interfaces below the source, in kilometers
            sourceVelocity : tuple of floats
                P or S velocity of each interval below the source, in kilometers
                per second
            receiverDepth : tuple of floats
                Depths of all the model interfaces below the receiver, in kilometers
            receiverVelocity : tuple of floats
                P or S velocity of each interval below the receiver, in kilometers
                per second
            npoints : int
                Nunber of points along the headwave path where velocity and gradient
                values are interpolated
            headWaveVelocity : tuple of floats
                P or S velocity at the center of each horizontal segment between the
                source and the receiver, in kilometers per seconds
            gradient : tuple of floats
                P or S velocity gradient in the mantle at the center of each
                horizontal segment of the head wave, in 1/seconds

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getGreatCircleData()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getGreatCircleLocations(self) -> Tuple[Tuple[float, ...], Tuple[float, ...], Tuple[float, ...]]:
            """Retrieve the latitudes, longitudes and depths of all the profile
            positions along the headwave interface.

            Profile positions are located at the center of each segment of the head
            wave interface between the source and receiver. The first position is
            located `actual_path_increment`/2 radians from the source, the last
            profile position is located `actual_path_increment`/2 radians from the
            receiver, and the others are spaced `actual_path_increment` radians
            apart.

            Examples
            --------
                >>> slbm.getGreatCircleLocations()

            Returns
            -------
            latitude : tuple of floats
                Latitude at the center of each headwave segment, in radians
            longitude : tuple of floats
                Longitude at the center of each headwave segment, in radians
            depth : tuple of floats
                Depth of the headwave interface at the center of each headwave
                segment, in kilometers

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getGreatCircleLocations()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getGreatCircleNodeInfo(self) -> Tuple[Tuple[Tuple[int, ...], ...], Tuple[Tuple[float, ...], ...]]:
            """Retrieve information about the interpolated points along the
            headwave path.

            Examples
            --------
                >>> slbm.getGreatCircleNodeInfo()

            Returns
            -------
            neighbors : tuple of tuples of ints
                Ragged 2D array of `ints` with dimensions `npoints` x `nnodes`
                containing the `nodeIds` of the neighboring grid nodes used to
                derive the interpolated data at each head wave profile
            coefficients : tuple of tuples of doubles
                Ragged 2D array of `doubles` with dimensions `npoints` x `nnodes`
                containing the interpolation coefficients applied to each element
                of `neighbors`

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getGreatCircleNodeInfo()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getGreatCirclePoints(self,
                lat1Rad: float, lon1Rad: float,
                lat2Rad: float, lon2Rad: float,
                npoints: int) -> Tuple[Tuple[float, ...], Tuple[float, ...]]:
            """Retrieve an array of latitude/longitude points along a great circle
            path between two specified points.

            The great circle path between the two points is divided into `npoints-1`
            equal size cells and the computed points are located at the boundaries
            of those cells. First point will coincide with the startnig point and
            last point with the ending point.

            Examples
            --------
                >>> slbm.getGreatCirclePoints(0.1, 0., 0.082, 0., 10)

            Parameters
            ----------
            lat1Rad : float
                Latitude of starting location, in radians
            lon1Rad : float
                Longitude of starting location, in radians
            lat2Rad : float
                Latitude of ending location, in radians
            lon2Rad : float
                Longitude of ending location, in radians
            npoints : int
                The desired number of points along the great circle

            Returns
            -------
            latitudes : tuple of floats
                The latitudes of the points along the great circle, in radians
            longitudes : tuple of floats
                The longitudes of the points along the great circle, in radians

            Raises
            ------
            TypeError
                Specified Lat/lon locations aren't all `float`
            ValueError
                An inappropriate number of points was requested
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: locations are all floats
            if not all(isinstance(arg, float) for arg in (lat1Rad, lon1Rad, lat2Rad, lon2Rad)):
                raise TypeError("Location latitude/longitudes should all be type 'float'")

            # ARG CHECK: number of requested points is >= 2
            if not npoints >= 2:
                raise ValueError("`npoints` must be at least 2")

            # try and call the function
            try:
                return super().getGreatCirclePoints(lat1Rad, lon1Rad, lat2Rad, lon2Rad, npoints)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getGreatCirclePointsOnCenters(self,
                lat1Rad: float, lon1Rad: float,
                lat2Rad: float, lon2Rad: float,
                npoints: int) -> Tuple[Tuple[float, ...], Tuple[float, ...]]:
            """Retrieve an array of latitude/longitude points along a great circle
            path between two specified points.

            The great circle path between the two points is divided into `npoints-1`
            equal size cells and the computed points are located at the centers of
            those cells. First point will coincide with the startnig point and last
            point with the ending point.

            Examples
            --------
                >>> slbm.getGreatCirclePointsOnCenters(0.1, 0., 0.082, 0., 10)

            Parameters
            ----------
            lat1Rad : float
                Latitude of starting location, in radians
            lon1Rad : float
                Longitude of starting location, in radians
            lat2Rad : float
                Latitude of ending location, in radians
            lon2Rad : float
                Longitude of ending location, in radians
            npoints : int
                The desired number of points along the great circle

            Returns
            -------
            latitudes : tuple of floats
                The latitudes of the points along the great circle, in radians
            longitudes : tuple of floats
                The longitudes of the points along the great circle, in radians

            Raises
            ------
            TypeError
                Specified Lat/lon locations aren't all `float`
            ValueError
                An inappropriate number of points was requested
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: locations are all floats
            if not all(isinstance(arg, float) for arg in (lat1Rad, lon1Rad, lat2Rad, lon2Rad)):
                raise TypeError("Location latitude/longitudes should all be type 'float'")

            # ARG CHECK: number of requested points is >= 2
            if not npoints >= 2:
                raise ValueError("`npoints` must be at least 2")

            # try and call the function
            try:
                return super().getGreatCirclePointsOnCenters(lat1Rad, lon1Rad, lat2Rad, lon2Rad, npoints)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getGridData(self, nodeId: int) -> Tuple[float, float,
                Tuple[float,...], Tuple[float,...], Tuple[float,...], Tuple[float,...]]:
            """Retrieve information associated with a specified node in the
            velocity grid.

            Retrieve the latitude, longitude, interface depths, P and S wave
            interval velocities and P and S mantle gradient information associated
            with a specified node in the velocity grid.

            Examples
            --------
                >>> slbm.getGridData(1001)

            Parameters
            ----------
            nodeId: int
                Node ID of the grid point in the model (zero based index)

            Returns
            -------
            latitude : float
                Latitude of the active node, in radians
            longitude : float
                Longitude of the active node, in radians
            depth : tuple of floats
                Depths of all the model interfaces, in kilometers
            pvelocity : tuple of floats
                P velocities of the intervals at the active node, in kilometers per second
            svelocity : tuple of floats
                S velocities of the intervals at the active node, in kilometers per second
            gradient : tuple of floats
                P and S velocity gradients in the mantle, in 1/second

            Raises
            ------
            TypeError
                `nodeId` isn't an `int`
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: nodeId is an int
            if not isinstance(nodeId, int):  # phase is an int or string
                raise TypeError("`nodeId` expects type 'int', received '{}'".format(type(nodeId).__name__))

            # try and call the function
            try:
                return super().getGridData(nodeId)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getGridNodeId(self, activeNodeId: int) -> int:
            """Retrieve the grid node ID that corresponds to a specified active node ID.

            Examples
            --------
                >>> slbm.getGridNodeId(11)

            Returns
            -------
            int
                Grid node ID

            Raises
            ------
            TypeError
                Provided node ID isn't `int`
            ValueError
                An inappropriate node ID was requested
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: activeNodeId is an int
            if not isinstance(activeNodeId, int):  # activeNodeId is an int
                raise TypeError("`activeNodeId` expects type 'int', received '{}'".format(type(activeNodeId).__name__))

            # ARG CHECK: activeNodeId >= 0
            if not activeNodeId >= 0:
                raise ValueError("`activeNodeId` must be greater than or equal to 0")

            # try and call the function
            try:
                return super().getGridNodeId(activeNodeId)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getHeadwaveDistance(self) -> float:
            """Retrieve the angular distance traveled by the ray below the headwave
            interface.

            This is the total distance minus the horizontal offsets below the source
            and receiver. :meth:`~SlbmInterface.getSourceDistance`
            + :meth:`~SlbmInterface.getReceiverDistance`
            + :meth:`~SlbmInterface.getHeadwaveDistance`
            = :meth:`~SlbmInterface.getDistance`.

            Examples
            --------
                >>> slbm.getHeadwaveDistance()

            Returns
            -------
            float
                Angular distance traveled by the ray below the headwave interface,
                in radians

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getHeadwaveDistance()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getHeadwaveDistanceKm(self) -> float:
            """Retrieve the horizontal distance traveled by the ray below the
            headwave interface.

            This is the sum of `actual_path_increment(i) * R(i)` where
            `actual_path_increment(i)` is the angular distance traveled by the ray
            in each angular distance increment along the head wave interface, and
            `R(i)` is the radius of the head wave interface in that same horizontal
            increment.

            Examples
            --------
                >>> slbm.getHeadwaveDistanceKm()

            Returns
            -------
            float
                Horizontal distance traveled by the ray below the headwave
                interface, in kilometers

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getHeadwaveDistanceKm()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getInterpolatedPoint(self, lat: float, lon: float) -> Tuple[Tuple[int, ...],
            Tuple[float, ...], Tuple[float, ...], Tuple[float, ...], Tuple[float, ...],
            float, float]:
            """Retrieve interpolated data from the earth model at a single specified
            latitude/longitude.

            Examples
            --------
                >>> slbm.getInterpolatedPoint(0.1, 0.2)

            Parameters
            ----------
            lat : float
                Latitude where information is to be interpolated, in radians
            lon : float
                Longitude where information is to be interpolated, in radians

            Returns
            -------
            nodeIds : tuple of ints
                Node IDs of the grid nodes that were involved in the interpolation
            coefficients : tuple of floats
                Interpolation coefficients that were applied to the information from
                the neighboring grid nodes
            depth : tuple of floats
                Depths of the tops of all the model interfaces, in kilometers
            pvelocity : tuple of floats
                P velocities of each layer of the model, in kilometers per second
            svelocity : tuple of floats
                S velocities of each layer of the model, in kilometers per second
            pgradient : float
                P velocity gradient in the mantle, in 1/second
            sgradient : float
                S velocity gradient in the mantle, in 1/second

            Raises
            ------
            TypeError
                Latitude/longitude aren't type `float`
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: lat/lon are floats
            if not all(isinstance(arg, float) for arg in (lat, lon)):
                raise TypeError("Latitude/longitude should be type 'float'")

            # try and call the function
            try:
                return super().getInterpolatedPoint(lat, lon)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getInterpolatedTransect(self,
                lat: Tuple[float, ...], lon: Tuple[float, ...]) -> Tuple[Tuple[Tuple[int, ...]],
                Tuple[Tuple[float, ...]], Tuple[Tuple[float, ...]],
                Tuple[Tuple[float, ...]], Tuple[Tuple[float, ...]],
                Tuple[float, ...], Tuple[float, ...], int]:
            """Retrieve interpolated data from the earth model along a transec
            defined by equal sized, 1D arrays of latitude and longitude.

            Examples
            --------
                >>> slbm.getInterpolatedTransect()

            Parameters
            ----------
            lat : tuple of floats
                Latitudes along the transect, in radians
            lon : tuple of floats
                Longitudes along the transect, in radians

            Returns
            -------
            nodeId : tuple of tuple of ints
                Node IDs of the grid nodes that were involved in the interpolations
            coefficients : tuple of tuple of floats
                Interpolation coefficients that were applied to the information from
                the neighboring grid nodes
            depth : tuple of tuple of floats
                Depth of the tops of the interfaces in the model, in kilometers
            pvelocity : tuple of tuple of floats
                P velocities of each layer of the model, in kilometers per second
            svelocity : tuple of tuple of floats
                S velocities of each layer of the model, in kilometers per second
            pgradient : tuple of floats
                Mantle P velocity gradient, in 1/seconds
            sgradient : tuple of floats
                Mantle S velocity gradient, in 1/sec
            nInvalid : int
                Number of points that were out of the model range

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getInterpolatedTransect(lat, lon)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getInterpolatorType(self) -> str:
            """Retrieve the type of interpolator currently in use; either "LINEAR"
            or "NATURAL_NEIGHBOR".

            Examples
            --------
                >>> slbm.getInterpolatorType()

            Returns
            -------
            str
                Type of interpolator currently in use

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getInterpolatorType()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getMaxDepth(self) -> float:
            """Retrieve the current value for the maximum source depth.

            Examples
            --------
                >>> slbm.getMaxDepth()

            Returns
            -------
            float
                Maximum source depth, in kilometers

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getMaxDepth()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getMaxDistance(self) -> float:
            """Retrieve the current value for the maximum source-receiver separation.

            Examples
            --------
                >>> slbm.getMaxDistance()

            Returns
            -------
            float
                Maximum source-receiver separation, in radians

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getMaxDistance()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getModelPath(self) -> str:
            """Return the path to the RSTT model.

            Examples
            --------
                >>> slbm.getModelPath()

            Returns
            -------
            str
                Path to the RSTT model

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getModelPath()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getModelString(self) -> str:
            """Calls :meth:`~SlbmInterface.toString` on the RSTT model.

            Examples
            --------
                >>> slbm.getModelString()

            Returns
            -------
            str
                Human-readable string representation of the RSTT model

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getModelString()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getNActiveNodes(self) -> int:
            """Retrieve the number of active nodes in the `Grid`.

            Examples
            --------
                >>> slbm.getNActiveNodes()

            Returns
            -------
            int
                Number of active nodes in the `Grid`

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getNActiveNodes()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getNGridNodes(self) -> int:
            """Retrieve the number of `Grid` nodes in the Earth model.

            Examples
            --------
                >>> slbm.getNGridNodes()

            Returns
            -------
            str
                Returns something

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getNGridNodes()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getNHeadWavePoints(self) -> int:
            """Retrieve the number of `LayerProfile` objects positioned along the
            head wave interface.

            Examples
            --------
                >>> slbm.getNHeadWavePoints()

            Returns
            -------
            int
                Number of `LayerProfile` objects positioned along the head wave
                interface

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getNHeadWavePoints()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getNodeAzimuth(self, node1: int, node2: int) -> float:
            """Retrieve the azimuth from `node1` to `node2`.

            Examples
            --------
                >>> slbm.getNodeAzimuth(123, 1001)

            Parameters
            ----------
            node1 : int
                ID of starting node
            node2 : int
                ID of ending node

            Returns
            -------
            float
                Azimuth from `node1` to `node2`

            Raises
            ------
            TypeError
                Specified node IDs aren't type `int`
            ValueError
                Inappropriate node IDs were supplied
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: nodes are all ints
            if not all(isinstance(arg, int) for arg in (node1, node2)):
                raise TypeError("Node IDs should all be type 'int'")

            # ARG CHECK: nodeids >= 0
            if not all([node >= 0 for node in (node1, node2)]):
                raise ValueError("Node IDs must be greater than or equal to zero")

            # try and call the function
            try:
                return super().getNodeAzimuth(node1, node2)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getNodeHitCount(self, nodeId: int) -> int:
            """Retrieve the number of times that the specified node has been
            'touched' by a `GreatCircle` object.

            The hit count of each node is initialized in the
            :meth:`~SlbmInterface.loadVelocityModel` method. Every time the
            :meth:`~SlbmInterface.getWeights` method is called for a particular `GreatCircle` object,
            all the `nodeIds` that contribute any `weight` to that `GreatCircle`
            object have their hit count incremented by one.

            Examples
            --------
                >>> slbm.getNodeHitCount(1001)

            Parameters
            ----------
            nodeId : int
                Node for which to query the hit count

            Returns
            -------
            int
                Number of times that the specified node has been 'touched'

            Raises
            ------
            TypeError
                Specified node ID isn't type `int`
            ValueError
                Inappropriate node ID was supplied
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: node is an int
            if not isinstance(nodeId, int):
                raise TypeError("Node ID should be type 'int'")

            # ARG CHECK: nodeId >= 0
            if not nodeId >= 0:
                raise ValueError("Node ID must be greater than or equal to zero")

            # try and call the function
            try:
                return super().getNodeHitCount(nodeId)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getNodeNeighborInfo(self, nodeId: int) -> Tuple[Tuple[int, ...],
                Tuple[float, ...], Tuple[float, ...]]:
            """Retrieve the IDs of the nodes that surround the specified node.

            Examples
            --------
                >>> slbm.getNodeNeighborInfo(1001)

            Returns
            -------
            neighbors : tuple of ints
                Neighbors of the specified node
            distance : tuple of floats
                Distance of the neighbors to the specified node
            azimuth : tuple of floats
                Azimuth of the neighbors to the specified node

            Raises
            ------
            TypeError
                Specified node ID isn't type `int`
            ValueError
                Inappropriate node ID was supplied
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: node is an int
            if not isinstance(nodeId, int):
                raise TypeError("Node ID should be type 'int'")

            # ARG CHECK: nodeId >= 0
            if not nodeId >= 0:
                raise ValueError("Node ID must be greater than or equal to zero")

            # try and call the function
            try:
                return super().getNodeNeighborInfo(nodeId)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getNodeNeighbors(self, nodeId: int) -> Tuple[int, ...]:
            """Retrieve the IDs of the nodes that surround the specified node.

            Examples
            --------
                >>> slbm.getNodeNeighbors(1001)

            Returns
            -------
            int
                Returns something

            Raises
            ------
            TypeError
                Specified node ID isn't type `int`
            ValueError
                Inappropriate node ID was supplied
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: node is an int
            if not isinstance(nodeId, int):
                raise TypeError("Node ID should be type 'int'")

            # ARG CHECK: nodeId >= 0
            if not nodeId >= 0:
                raise ValueError("Node ID must be greater than or equal to zero")

            # try and call the function
            try:
                return super().getNodeNeighbors(nodeId)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getNodeSeparation(self, node1: int, node2: int) -> float:
            """Retrieve the angular separation of two grid nodes.

            Examples
            --------
                >>> slbm.getNodeSeparation(123, 1001)

            Returns
            -------
            float
                Angular separation of `node1` and `node2`, in radians

            Raises
            ------
            TypeError
                Specified node IDs aren't type `int`
            ValueError
                Inappropriate node IDs were supplied
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: nodes are all ints
            if not all(isinstance(arg, int) for arg in (node1, node2)):
                raise TypeError("Node IDs should all be type 'int'")

            # ARG CHECK: nodeids >= 0
            if not all([node >= 0 for node in (node1, node2)]):
                raise ValueError("Node IDs must be greater than or equal to zero")

            # try and call the function
            try:
                return super().getNodeSeparation()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getPathIncrement(self) -> float:
            """Retrieve the current value of the spacing of great circle nodes along
            the head wave interface.

            The actual spacing will be reduced from the requested value in order
            that an integral number of equally spaced `LayerProfile` objects will
            exactly span the source-receiver separation.

            The default value is 0.1 degrees.

            Examples
            --------
                >>> slbm.getPathIncrement()

            Returns
            -------
            float
                Spacing of the great circle nodes along the head wave interface,
                in radians

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getPathIncrement()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getPgLgComponents(self):
            """Retrieve information about Pg/Lg travel time calculations.

            This method only returns useful information when the phase is `Pg` or `Lg.`

            `tTotal` will be exactly equal to the lesser of `tTaup` or `tHeadwave`.

            Examples
            --------
                >>> slbm.getPgLgComponents()

            Returns
            -------
            tTotal : float
                Total travel time, in seconds
            tTaup : float
                TauP travel time, in seconds
            tHeadwave : float
                Headwave travel time, in seconds
            pTaup : float
                TauP ray parameter
            pHeadwave : float
                Headwave ray parameter
            trTaup : float
                Radius at which the taup ray turned, in kilometers
            trHeadwave : float
                Radius at which the headwave ray turned, in kilometers

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getPgLgComponents()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getPhase(self) -> str:
            """Retrieve the phase specified in last call to
            :meth:`~SlbmInterface.createGreatCircle`.

            Examples
            --------
                >>> slbm.getPhase()

            Returns
            -------
            str
                The phase specified in last call to :meth:`~SlbmInterface.createGreatCircle`

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getPhase()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getPiercePointReceiver(self) -> Tuple[float, float, float]:
            """Retrieve the location of the Moho pierce point below the receiver.

            For Pg, Lg an exception is thrown.

            Examples
            --------
                >>> slbm.getPiercePointReceiver()

            Returns
            -------
            latitude : float
                Latitude of the Moho pierce point below the receiver, in radians
            longitude : float
                Longitude of the Moho pierce point below the receiver, in radians
            depth : float
                Depth of the Moho pierce point below the receiver, in kilometers

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getPiercePointReceiver()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getPiercePointSource(self):
            """Retrieve the location of the Moho pierce point below the source.

            For Pg, Lg an exception is thrown.

            Examples
            --------
                >>> slbm.getPiercePointReceiver()

            Returns
            -------
            latitude : float
                Latitude of the Moho pierce point below the source, in radians
            longitude : float
                Longitude of the Moho pierce point below the source, in radians
            depth : float
                Depth of the Moho pierce point below the source, in kilometers

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getPiercePointSource()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getRayParameter(self) -> float:
            """Retrieve the ray parameter.

            Examples
            --------
                >>> slbm.getRayParameter()

            Returns
            -------
            float
                Ray parameter

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getRayParameter()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getReceiverDistance(self) -> float:
            """Retrieve horizontal offset below the receiver.

            This is the angular distance between the location of the receiver and
            the receiver pierce point where the ray impinged on the headwave
            interface.

            Examples
            --------
                >>> slbm.getReceiverDistance()

            Returns
            -------
            float
                Horizontal offset below the receiver, in radians

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getReceiverDistance()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getSlowness(self) -> float:
            """Retrieve the horizontal slowness (i.e., the derivative of travel time
            with respect to receiver-source distance).

            Examples
            --------
                >>> slbm.getSlowness()

            Returns
            -------
            float
                Horizontal slownessm in seconds/radian

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getSlowness()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getSlownessUncertainty(self) -> float:
            """Retrieve uncertainty of the horizontal slowness using the phase and
            distance specified in last call to :meth:`~SlbmInterface.getGreatCircle`.

            Examples
            --------
                >>> slbm.getSlownessUncertainty()

            Returns
            -------
            float
                Uncertainty of the horizontal slowness, in seconds per radian

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getSlownessUncertainty()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getSourceDistance(self) -> float:
            """Retrieve horizontal offset below the source.

            This is the angular distance between the location of the source and
            the source pierce point where the ray impinged on the headwave
            interface.

            Examples
            --------
                >>> slbm.getSourceDistance()

            Returns
            -------
            float
                Horizontal offset below the source, in radians

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getSourceDistance()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getTessId(self) -> str:
            """Retrieve the tessellation ID of the model currently in memory.

            Examples
            --------
                >>> slbm.getTessId()

            Returns
            -------
            str
                Tessellation ID of the model currently in memory

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getTessId()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getTravelTime(self) -> float:
            """Retrieve the total travel time for the `GreatCircle`.

            Examples
            --------
                >>> slbm.getTravelTime()

            Returns
            -------
            float
                Total travel time for the `GreatCircle`, in seconds

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getTravelTime()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getTravelTimeComponents(self) -> Tuple[float, float, float, float, float]:
            """Retrieve the total travel time and the four components that
            contribute to it for the current GreatCircle.

            Examples
            --------
                >>> slbm.getTravelTimeComponents()

            Returns
            -------
            tTotal : float
                Total travel time, in seconds
            tSource : float
                Crustal travel time below the source, in seconds
            tReceiver : float
                Crustal travel time below the receiver, in seconds
            tHeadwave : float
                Head wave travel time, in seconds
            tGradient : float
                Zhao gradient correction term, in seconds

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getTravelTimeComponents()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getTravelTimeUncertainty(self, useRandomError: bool = False) -> float:
            """Returns the path-dependent travel time uncertainty (PDU), in seconds

            Returns the path-dependent travel time uncertainty (PDU) for the
            `GreatCircle`, in seconds. Path-dependent uncertainty is computed
            with *model error*, *bias*, and (optionally) *random error* (Begnaud
            et al., 2020). By default, *random error* is not used in the
            computation.

            Examples
            --------
                >>> slbm.getTravelTimeUncertainty()
                3.9911

                Use the *random error* values in the uncertainty calculation

                >>> slbm.getTravelTimeUncertainty(True)
                4.0463

            Parameters
            ----------
            useRandomError : bool
                Determines whether or not *random error* is used in the travel time
                uncertainty computation.

            Returns
            -------
            float
                Returns the path-dependent travel time uncertainty (PDU), in seconds

            Raises
            ------
            TypeError
                `useRandomError` is not a a `bool`, or too many arguments were supplied
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # some error checking
            if not isinstance(useRandomError, bool):  # verbosity is an int
                raise TypeError("`useRandomError` expects type 'bool', received '{}'".format(type(useRandomError).__name__))

            # try and call the function
            try:
                return super().getTravelTimeUncertainty(useRandomError)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        # alias path-dependent `getTravelTimeUncertainty` to `getTravelTimeUncertaintyPDU`
        getTravelTimeUncertaintyPDU = getTravelTimeUncertainty

        def getTravelTimeUncertainty1D(self) -> float:
            """Returns the path-independent travel time uncertainty (PIU), in seconds

            Returns the path-independent travel time uncertainty (PIU) for the
            `GreatCircle`, in seconds. This was the standard uncertainty computation
            prior to RSTT v3.1.0.

            Examples
            --------
                >>> slbm.getTravelTimeUncertainty()
                1.1542

            Returns
            -------
            float
                Returns the path-independent travel time uncertainty (PIU), in seconds

            Raises
            ------
            TypeError
                Too many arguments were supplied
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getTravelTimeUncertainty1D()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        # alias path-independent `getTravelTimeUncertainty1D` to `getTravelTimeUncertaintyPIU`
        getTravelTimeUncertaintyPIU = getTravelTimeUncertainty1D

        def getTurningRadius(self) -> float:
            """Retrieve the turning radius of the ray.

            Examples
            --------
                >>> slbm.getTurningRadius()

            Returns
            -------
            float
                Turning radius of the ray

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getTurningRadius()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getUncertaintyFileFormat(self, phase: int or str, attribute: int or str) -> str:
            """Return path-independent uncertainty information related to the
            specified `phase` and `attribute` in the format of an ASCII model.

            Examples
            --------
                >>> slbm.getUncertaintyFileFormat(0, 1)

                >>> slbm.getUncertaintyFileFormat('Pn', 'SH')

            Parameters
            ----------
            phase : int or str
                A phase name, or associated number. Accepted values are
                    * `Pn` or `0`
                    * `Sn` or `1`
                    * `Pg` or `2`
                    * `Lg` or `3`
            attribute : int or str
                An attribute name, or associated number. Accepted values are
                    * `TT` or `0`
                    * `SH` or `1`
                    * `AZ` or `2`

            Returns
            -------
            str
                Path-independent uncertainty information related to the specified
                `phase` and `attribute`.

            Raises
            ------
            TypeError
                `phase` or `attribute` aren't an `int` or a `str`
            ValueError
                An inappropriate `phase` or `attribute` was supplied
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: phase is an int or str
            if not isinstance(phase, (int, str)):  # phase is an int or string
                raise TypeError("`phase` expects type 'int' or 'str', received '{}'".format(type(phase).__name__))

            # ARG CHECK: str phase is one of [Pn, Sn, Pg, Lg]
            if isinstance(phase, str):
                if phase.lower() not in ('pn', 'sn', 'pg', 'lg'):
                    raise ValueError("`phase` must be one of: 'Pn', 'Sn', 'Pg', or 'Lg'")

            # ARG CHECK: int phase is one of [0, 1, 2, 3]
            if isinstance(phase, int):
                if phase not in (0, 1, 2, 3):
                    raise ValueError("`phase` must be one of: 0 (Pn), 1 (Sn), 2 (Pg), or 3 (Lg)")

            # ARG CHECK: attribute is an int or str
            if not isinstance(attribute, (int, str)):  # attribute is an int or string
                raise TypeError("`attribute` expects type 'int' or 'str', received '{}'".format(type(attribute).__name__))

            # ARG CHECK: str attribute is one of [TT, SH, AZ]
            if isinstance(attribute, str):
                if attribute.lower() not in ('tt', 'sh', 'az'):
                    raise ValueError("`phase` must be one of: 'TT', 'SH', or 'AZ'")

            # ARG CHECK: int attribute is one of [0, 1, 2]
            if isinstance(attribute, int):
                if attribute not in (0, 1, 2):
                    raise ValueError("`attribute` must be one of: 0 (TT), 1 (SH), or 2 (AZ)")

            # convert str phase and attribute to ints
            if isinstance(phase, str):
                phase = phases(phase)
            if isinstance(attribute, str):
                attribute = attributes(attribute)

            # try and call the function
            try:
                return super().getUncertaintyFileFormat(phase, attribute)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getUncertaintyTable(self, phase: int or str, attribute: int or str) -> str:
            """Return path-independent uncertainty information related to the
            specified `phase` and `attribute` in a table format.

            Examples
            --------
                >>> slbm.getUncertaintyTable(0, 1)

                >>> slbm.getUncertaintyTable('Pn', 'SH')

            Parameters
            ----------
            phase : int or str
                A phase name, or associated number. Accepted values are
                    * `Pn` or `0`
                    * `Sn` or `1`
                    * `Pg` or `2`
                    * `Lg` or `3`
            attribute : int or str
                An attribute name, or associated number. Accepted values are
                    * `TT` or `0`
                    * `SH` or `1`
                    * `AZ` or `2`

            Returns
            -------
            str
                Path-independent uncertainty information related to the specified
                `phase` and `attribute`.

            Raises
            ------
            TypeError
                `phase` or `attribute` aren't an `int` or a `str`
            ValueError
                An inappropriate `phase` or `attribute` was supplied
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: phase is an int or str
            if not isinstance(phase, (int, str)):  # phase is an int or string
                raise TypeError("`phase` expects type 'int' or 'str', received '{}'".format(type(phase).__name__))

            # ARG CHECK: str phase is one of [Pn, Sn, Pg, Lg]
            if isinstance(phase, str):
                if phase.lower() not in ('pn', 'sn', 'pg', 'lg'):
                    raise ValueError("`phase` must be one of: 'Pn', 'Sn', 'Pg', or 'Lg'")

            # ARG CHECK: int phase is one of [0, 1, 2, 3]
            if isinstance(phase, int):
                if phase not in (0, 1, 2, 3):
                    raise ValueError("`phase` must be one of: 0 (Pn), 1 (Sn), 2 (Pg), or 3 (Lg)")

            # ARG CHECK: attribute is an int or str
            if not isinstance(attribute, (int, str)):  # attribute is an int or string
                raise TypeError("`attribute` expects type 'int' or 'str', received '{}'".format(type(attribute).__name__))

            # ARG CHECK: str attribute is one of [TT, SH, AZ]
            if isinstance(attribute, str):
                if attribute.lower() not in ('tt', 'sh', 'az'):
                    raise ValueError("`phase` must be one of: 'TT', 'SH', or 'AZ'")

            # ARG CHECK: int attribute is one of [0, 1, 2]
            if isinstance(attribute, int):
                if attribute not in (0, 1, 2):
                    raise ValueError("`attribute` must be one of: 0 (TT), 1 (SH), or 2 (AZ)")

            # convert str phase and attribute to ints
            if isinstance(phase, str):
                phase = phases(phase)
            if isinstance(attribute, str):
                attribute = attributes(attribute)

            # try and call the function
            try:
                return super().getUncertaintyTable(phase, attribute)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getWeights(self) -> Tuple[Tuple[int, ...], Tuple[float, ...]]:
            """Retrieve the weight assigned to each grid node that was touched by
            the `GreatCircle`.

            Each grid node is included only once, even though more than one
            `LayerProfile` object may have contributed some weight to it. The sum of
            all the weights will equal the horizontal distance traveled by the ray
            along the head wave interface, from the source pierce point to the
            receiver pierce point, in kilometers.

            Note: This method returns active node IDs, not grid node IDs. if a grid
            node has weight but is not an active node, the node ID will be -1.

            Examples
            --------
                >>> slbm.getWeights()

            Returns
            -------
            nodeId : tuple of ints
                Active node IDs of all the grid nodes touched by the current `GreatCircle`
            weights : tuple of floats
                Weights of all the grid nodes touched by the current `GreatCircle`

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getWeights()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getWeightsReceiver(self) -> Tuple[Tuple[int, ...], Tuple[float, ...]]:
            """Retrieve the node IDs and the interpolation coefficients for the
            receiver `CrustalProfile`.

            For linear interpolation the number of weights will equal 3, but for
            natural neighbor interpolation it will be variable but less than 10. The
            sum of the weights will equal 1.

            Examples
            --------
                >>> slbm.getWeightsReceiver()

            Returns
            -------
            nodeId : tuple of ints
                Active node IDs of all the grid nodes touched by the current `GreatCircle`
            weights : tuple of floats
                Weights of all the grid nodes touched by the current `GreatCircle`

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getWeightsReceiver()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getWeightsSource(self) -> Tuple[Tuple[int, ...], Tuple[float, ...]]:
            """Retrieve the node IDs and the interpolation coefficients for the
            source `CrustalProfile`.

            For linear interpolation the number of weights will equal 3, but for
            natural neighbor interpolation it will be variable but less than 10. The
            sum of the weights will equal 1.

            Examples
            --------
                >>> slbm.getWeightsSource()

            Returns
            -------
            nodeId : tuple of ints
                Active node IDs of all the grid nodes touched by the current `GreatCircle`
            weights : tuple of floats
                Weights of all the grid nodes touched by the current `GreatCircle`

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getWeightsSource()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def getZhaoParameters(self) -> Tuple[float, float, float, float, float, int]:
            """Retrieve some of the parameters that contribute to the calculation
            of total travel time using the Zhao algorithm.

            This method only returns meaningful results for phases Pn and Sn.

            Examples
            --------
                >>> slbm.getZhaoParameters()

            Returns
            -------
            Vm : float
                Velocity at the top of the mantle, averaged along the Moho between
                the source and receiver pierce points
            Gm : float
                Velocity gradient at the top of the mantle, averaged along the Moho
                between the source and receiver pierce points
            H : float
                Turning depth of the ray relative to the Moho
            C : float
                Constant whose product with `V0` gives the mantle velocity gradient
                for a flat Earth (`V0` is the velocity of the top of the mantle
                averaged over the whole model)
            Cm : float
                Constant whose product with `Vm` gives the mantle velocity gradient
                for a flat Earth
            udSign : int
                Value indicates:
                    * 0, the source is in the crust
                    * +1, the ray leaves a mantle source in the downgoing direction
                    * -1, the ray leaves a mantle source in an upgoing direction

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().getZhaoParameters()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def get_dtt_ddepth(self) -> float:
            """Retrieve the derivative of travel time with respect to source depth.

            Long description

            Examples
            --------
                >>> slbm.get_dtt_ddepth()

            Returns
            -------
            float
                Derivative of travel time with respect to source depth, in seconds
                per kilometer

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().get_dtt_ddepth()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def get_dtt_ddist(self) -> float:
            """Retrieve the horizontal slowness, i.e., the derivative of travel time
            with respect to receiver-source distance.

            Long description

            Examples
            --------
                >>> slbm.get_dtt_ddepth()

            Returns
            -------
            float
                Horizontal slowness, in seconds per radian

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().get_dtt_ddist()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def get_dtt_dlat(self) -> float:
            """Retrieve the derivative of travel time with respect to source latitude.

            Examples
            --------
                >>> slbm.get_dtt_dlat()

            Returns
            -------
            float
                Derivative of travel time with respect to source latitude, in
                seconds per radian

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().get_dtt_dlat()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def get_dtt_dlon(self) -> float:
            """Retrieve the derivative of travel time with respect to source longitude.

            Examples
            --------
                >>> slbm.get_dtt_dlon()

            Returns
            -------
            float
                Derivative of travel time with respect to source longitude, in
                seconds per radian

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().get_dtt_dlon()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def initializeActiveNodes(self,
                latMinRad: float, lonMinRad: float,
                latMaxRad: float, lonMaxRad: float) -> None:
            """Set grid nodes within a latitude/longitude range as active nodes.

            Active nodes are defined as follows: for each triangle in the
            tessellation, if any of the 3 nodes that define the triangle is within
            the range specified by this method, then all 3 nodes are defined to be
            active nodes. Lats and lons must be specified in radians.

            Examples
            --------
                >>> slbm.initializeActiveNodes(0., 0., 0.1, 0.1)

            Parameters
            ----------
            latMinRad : float
                Minimum latitude, in radians
            lonMinRad : float
                Minimum longitude, in radians
            latMaxRad : float
                Maximum latitude, in radians
            lonMaxRad : float
                Maximum longitude, in radians

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: locations are all floats
            if not all(isinstance(arg, float) for arg in (latMinRad, lonMinRad, latMaxRad, lonMaxRad)):
                raise TypeError("Latitudes/longitudes should all be type 'float'")

            # try and call the function
            try:
                return super().initializeActiveNodes(latMinRad, lonMinRad, latMaxRad, lonMaxRad)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def isValid(self) -> bool:
            """Returns true if a `GreatCircle` object has been instantiated and is
            ready to be interrogated.

            Examples
            --------
                >>> slbm.isValid()

            Returns
            -------
            bool
                True if a `GreatCircle` object has been instantiated and is ready
                to be interrogated.

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().isValid()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def loadVelocityModel(self, model_path: str) -> None:
            """Load the velocity model into memory from the specified file or directory

            Load the velocity model into memory from the specified file or directory.

            Examples
            --------
                >>> slbm.loadVelocityModel("../models/example.geotess")

            Parameters
            ----------
            model_path : str
                Path to RSTT model, e.g., `/path/to/modelfile.geotess`. Relative
                path names are accepted.

            Raises
            ------
            TypeError
                `model_path` is not a `str`, or too many arguments were supplied
            FileNotFoundError
                The specified `model_path` was not found
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: model_path is a str
            if not isinstance(model_path, str):
                raise TypeError("`model_path` expects type 'str', received '{}'".format(type(model_path).__name__))

            # ARG CHECK: model_path exists
            if not os.path.exists(model_path):
                raise FileNotFoundError("File does not exist: {}".format(model_path))

            # try and call the function
            try:
                super().loadVelocityModel(model_path)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def movePoint(self, lat1: float, lon1: float,
                distance: float, azimuth: float) -> Tuple[float, float]:
            """Find point B that is the specified distance and azimuth from point A.

            Examples
            --------
                >>> slbm.movePoint(0., 0., .1, 0.)

            Parameters
            ----------
            lat1 : float
                Latitude of point A, in radians
            lon1 : float
                longitude of point A, in radians
            distance : float
                Angular distance from point A to point B, in radians
            azimuth : float
                Azimuth from pointA to point B, clockwise from north, in radians

            Returns
            -------
            lat2 : float
                Latitude of point B, in radians
            lon2 : float
                longitude of point B, in radians

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # try and call the function
            try:
                return super().movePoint()

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def saveVelocityModel(self, modelFileName: str, modelFormat: int = 4) -> None:
            """Save the velocity model currently in memory to the specified file or
            directory.

            The following `formats` are supported:

                1. SLBM version 1 ascii file. All model information is output to a
                   single file in ascii format. This format was available in SLBM
                   version 2, but never used.

                2. SLBM version 2 directory format. Model information is output to
                   a number of different files and directories, mostly in binary
                   format. This format was used almost exclusively in SLBM version 2.

                3. SLBM version 3 directory format. Model information is output to
                   a number of different files and directories, mostly in binary
                   format. This format is very similar to format 2 with the
                   difference being that the model tessellation and values are
                   stored in GeoTess format instead of the custom SLBM format.

                4. SLBM version 4 single-file format. **This is the default and
                   preferred format.** All model information is written to a single
                   file. If the `modelFileName` extension is `.ascii` the file is
                   written in ascii format, otherwise it is written in binary
                   format.

            See `SLBM_Design.pdf` in the main documentation directory for detailed
            information about model output formats. Models stored in SLBM version 1
            and 2 formats (formats 1 and 2) only support linear interpolation.
            Models stored in SLBM version 3 formats (formats 3 and 4) support both
            linear and natural neighbor interpolation.

            Examples
            --------
                >>> slbm.saveVelocityModel("example.geotess")

                >>> slbm.saveVelocityModel("example.geotess", 4)

            Parameters
            ----------
            modelFileName : str
                Full or relative path to the file or directory to which the earth
                model is to be written
            modelFormat : int
                File format version of the output (default = 4)

            Raises
            ------
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: modelFileName is a str
            if not isinstance(modelFileName, str):  # modelFileName is a str
                raise TypeError("`modelFileName` expects type 'str', received '{}'".format(type(modelFileName).__name__))

            # ARG CHECK: modelFormat is an int
            if not isinstance(modelFormat, int):  # modelFormat is an int
                raise TypeError("`modelFormat` expects type 'int', received '{}'".format(type(modelFormat).__name__))

            # ARG CHECK: modelFormat is one of [1, 2, 3, 4]
            if isinstance(modelFormat, int):
                if modelFormat not in (1, 2, 3, 4):
                    raise ValueError("`modelFormat` must be one of: 1, 2, 3, or 4 (preferred)")

            # try and call the function
            try:
                return super().saveVelocityModel(modelFileName, modelFormat)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def setActiveNodeData(self, nodeId: int,
                depths: Tuple[float, ...], pvelocity: Tuple[float, ...],
                svelocity: Tuple[float, ...], gradient: Tuple[float, float]) -> None:
            """Modify the depth, velocity and gradient information associated with
            a specified active node in the `Grid`.

            Examples
            --------
                >>> slbm.setActiveNodeData(11, [-2.7, ..., 36.2], [1.5, ..., 8.1],
                                               [9e-5, ..., 4.5], [0.0017, 0.0017])

            Parameters
            -------
            nodeId : int
                Node number of the grid point in the model
            depths : tuple of floats
                Depths of the tops of the layers, in kilometers
            pvelocity : tuple of floats
                P velocities of all the intervals at the specified grid node, in
                kilometers per second
            svelocity : tuple of floats
                S velocities of all the intervals at the specified grid node, in
                kilometers per second
            gradient : tuple of floats
                P and S velocity gradients in the mantle, in 1/second

            Raises
            ------
            TypeError
                `nodeId` is not an int or remaining parameters are not lists/tuples
                of floats
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: nodeId is an int
            if not isinstance(nodeId, int):  # nodeId is an int
                raise TypeError("`nodeId` expects type 'int', received '{}'".format(type(nodeId).__name__))

            # ARG CHECK: all remaining parameters are lists or tuples
            if not all(isinstance(arg, (list, tuple)) for arg in (depths, pvelocity, svelocity, gradient)):
                raise TypeError("Parameters should be lists or tuples of floats")

            # ARG CHECK: all remaining parameters contain only floats
            if not all(isinstance(val, float) for val in depths):
                raise TypeError("Contents of `depths` should all be type 'float'")
            if not all(isinstance(val, float) for val in pvelocity):
                raise TypeError("Contents of `pvelocity` should all be type 'float'")
            if not all(isinstance(val, float) for val in svelocity):
                raise TypeError("Contents of `svelocity` should all be type 'float'")
            if not all(isinstance(val, float) for val in gradient):
                raise TypeError("Contents of `gradient` should all be type 'float'")

            # try and call the function
            try:
                return super().setActiveNodeData(nodeId, depths, pvelocity, svelocity, gradient)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def setAverageMantleVelocity(self, waveType: int or str, velocity: float) -> None:
            """Set the average P or S wave mantle velocity.

            Examples
            --------
                >>> slbm.setAverageMantleVelocity('P', 8.1)

                >>> slbm.setAverageMantleVelocity(0, 8.1)

            Parameters
            ----------
            waveType : str or int
                Seismic wave type. Accepted values are
                    * :attr:`~rstt.PWAVE`, `P`, or `0`
                    * :attr:`~rstt.SWAVE`, `S`, or `1`
            velocity : float
                P or S wave velocity that is to be set, in kilometers per second

            Raises
            ------
            TypeError
                `waveType` isn't an `int` or a `str`
            ValueError
                An inappropriate `waveType` was supplied
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: waveType is and int or str
            if not isinstance(waveType, (int, str)):  # waveType is an int or string
                raise TypeError("`waveType` expects type 'int' or 'str', received '{}'".format(type(waveType).__name__))

            # ARG CHECK: str waveType is one of [P, S]
            if isinstance(waveType, str):
                if waveType.lower() not in ('p', 's'):
                    raise ValueError("`waveType` must be either 'P' or 'S'")

            # ARG CHECK: int waveType is one of [0, 1]
            if isinstance(waveType, int):
                if waveType not in (0, 1):
                    raise ValueError("`waveType` must be 0 (P) or 1 (S)")

            # convert string waveType to int
            if isinstance(waveType, str):
                waveType = PWAVE if waveType.lower() == 'p' else SWAVE

            # try and call the function
            try:
                return super().setAverageMantleVelocity(waveType, velocity)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def setCHMax(self, CH_MAX: float) -> None:
            """Set the current value of CH_MAX.

            This call sets the global parameter :attr:`~SlbmInterface.CH_MAX`.
            Alternatively, this parameter may be set by calling it as an attribute
            of the current :class:`SlbmInterface` object.

            `c` is the Zhao `c` parameter, and `h` is the turning depth of the ray
            below the Moho. The Zhao method only valid for `c*h << 1`. When `c*h >
            CH_MAX`, then RSTT will throw an exception.

            Examples
            --------
                >>> slbm.setCHMax(0.2)

                >>> slbm.CH_MAX = 0.2

            Parameters
            ----------
            CH_MAX : float
                Global :attr:`~SlbmInterface.CH_MAX` parameter

            Raises
            ------
            TypeError
                `CH_MAX` isn't a `float`
            ValueError
                An inappropriate `CH_MAX` was supplied
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: CH_MAX is a float
            if not isinstance(CH_MAX, float):  # CH_MAX is a float
                raise TypeError("`CH_MAX` expects type 'float', received '{}'".format(type(CH_MAX).__name__))

            # ARG CHECK: CH_MAX > 0
            if not CH_MAX > 0:
                raise ValueError("`CH_MAX` must be greater than zero")

            # try and call the function
            try:
                return super().setCHMax(CH_MAX)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def setDelDepth(self, delDepth: float) -> None:
            """Change the value of step change in depth used to compute depth
            derivatives.

            Examples
            --------
                >>> slbm.setDelDepth(0.1)

            Parameters
            ----------
            delDepth : float
                Step change in depth, in kilometers

            Raises
            ------
            TypeError
                `delDepth` isn't a `float`
            ValueError
                An inappropriate `delDepth` was supplied
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: delDepth is a float
            if not isinstance(delDepth, float):  # delDepth is a float
                raise TypeError("`delDepth` expects type 'float', received '{}'".format(type(delDepth).__name__))

            # ARG CHECK: delDepth > 0
            if not delDepth > 0:
                raise ValueError("`delDepth` must be greater than zero")

            # try and call the function
            try:
                return super().setDelDepth(delDepth)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def setDelDistance(self, delDistance: float) -> None:
            """Change the value of step change in distance used to compute
            horizontal derivatives.

            Examples
            --------
                >>> slbm.setDelDistance(0.1)

            Parameters
            ----------
            delDistance : float
                Step change in distance, in radians

            Raises
            ------
            TypeError
                `delDistance` isn't a `float`
            ValueError
                An inappropriate `delDistance` was supplied
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: delDistance is a float
            if not isinstance(delDistance, float):  # delDistance is a float
                raise TypeError("`delDepth` expects type 'float', received '{}'".format(type(delDistance).__name__))

            # ARG CHECK: delDistance > 0
            if not delDistance > 0:
                raise ValueError("`delDistance` must be greater than zero")

            # try and call the function
            try:
                return super().setDelDistance(delDistance)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def setGridData(self, nodeId: int,
                depths: Tuple[float, ...], pvelocity: Tuple[float, ...],
                svelocity: Tuple[float, ...], gradient: Tuple[float, float]) -> None:
            """Modify the depth, velocity and gradient information associated with
            a specified node in the `Grid`.

            Examples
            --------
                >>> slbm.setGridData(11, [-2.7, ..., 36.2], [1.5, ..., 8.1],
                                         [9e-5, ..., 4.5], [0.0017, 0.0017])

            Parameters
            -------
            nodeId : int
                Node number of the grid point in the model
            depths : tuple of floats
                Depths of the tops of the layers, in kilometers
            pvelocity : tuple of floats
                P velocities of all the intervals at the specified grid node, in
                kilometers per second
            svelocity : tuple of floats
                S velocities of all the intervals at the specified grid node, in
                kilometers per second
            gradient : tuple of floats
                P and S velocity gradients in the mantle, in 1/second

            Raises
            ------
            TypeError
                `nodeId` is not an int or remaining parameters are not lists/tuples
                of floats
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: nodeId is an int
            if not isinstance(nodeId, int):  # nodeId is an int
                raise TypeError("`nodeId` expects type 'int', received '{}'".format(type(nodeId).__name__))

            # ARG CHECK: all remaining parameters are lists or tuples
            if not all(isinstance(arg, (list, tuple)) for arg in (depths, pvelocity, svelocity, gradient)):
                raise TypeError("Parameters should be lists or tuples of floats")

            # ARG CHECK: all remaining parameters contain only floats
            if not all(isinstance(val, float) for val in depths):
                raise TypeError("Contents of `depths` should all be type 'float'")
            if not all(isinstance(val, float) for val in pvelocity):
                raise TypeError("Contents of `pvelocity` should all be type 'float'")
            if not all(isinstance(val, float) for val in svelocity):
                raise TypeError("Contents of `svelocity` should all be type 'float'")
            if not all(isinstance(val, float) for val in gradient):
                raise TypeError("Contents of `gradient` should all be type 'float'")

            # try and call the function
            try:
                return super().setGridData(nodeId, depths, pvelocity, svelocity, gradient)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def setInterpolatorType(self, interpolatorType: str) -> None:
            """Specify the interpolation type to use.

            With models loaded in the old RSTT formats 1 and 2, 'linear' is the only
            option allowed.

            Examples
            --------
                >>> slbm.setInterpolatorType('natural_neighbor')

            Parameters
            ----------
            interpolatorType : str
                Interpolation type, accepted values are:
                    * linear
                    * natural_neighbor

            Raises
            ------
            TypeError
                `interpolatorType` is not a str, or too many arguments were supplied
            ValueError
                An inappropriate `interpolatorType` value was supplied
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: interpolatorType is a str
            if not isinstance(interpolatorType, str):  # interpolatorType is a string
                raise TypeError("`interpolatorType` expects type 'str', received '{}'".format(type(interpolatorType).__name__))

            # ARG CHECK: str phase is one of ['linear', 'natural_neighbor']
            if interpolatorType.lower() not in ('linear', 'natural_neighbor'):
                raise ValueError("`interpolatorType` must be one of: 'linear', 'natural_neighbor'")

            # try and call the function
            try:
                return super().setInterpolatorType(interpolatorType)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def setMaxDepth(self, maxDepth: float) -> None:
            """Set the maximum source depth for Pn/Sn phase.

            Examples
            --------
                >>> slbm.setMaxDepth(200.)

            Parameters
            -------
            maxDepth : float
                Maximum source depth for Pn/Sn phase, in kilometers

            Raises
            ------
            TypeError
                `maxDepth` is not a float, or too many arguments were supplied
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: maxDepth is a float
            if not isinstance(maxDepth, float):  # maxDepth is a float
                raise TypeError("`maxDepth` expects type 'float', received '{}'".format(type(maxDepth).__name__))

            # try and call the function
            try:
                return super().setMaxDepth(maxDepth)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def setMaxDistance(self, maxDistance: float) -> None:
            """Set the maximum source-receiver separation for Pn/Sn phase.

            Examples
            --------
                >>> slbm.setMaxDistance(0.261)

            Parameters
            -------
            maxDistance : float
                Maximum source-receiver separation for Pn/Sn phase, in radians

            Raises
            ------
            TypeError
                `maxDistance` is not a float, or too many arguments were supplied
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: maxDistance is a float
            if not isinstance(maxDistance, float):  # maxDistance is a float
                raise TypeError("`maxDistance` expects type 'float', received '{}'".format(type(maxDistance).__name__))

            # try and call the function
            try:
                return super().setMaxDistance(maxDistance)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def setPathIncrement(self, pathIncrement: float) -> None:
            """Set the desired spacing of great circle nodes along the head wave
            interface.

            The actual spacing will be reduced from the requested value in order
            that an integral number of equally spaced `LayerProfile` objects will
            exactly span the source-receiver separation.

            Defaults to 0.1 degrees if not specified.

            Examples
            --------
                >>> slbm.setPathIncrement(0.00174)

            Parameters
            ----------
            pathIncrement : float
                Desired spacing of great circle nodes along the head wave interface,
                in radians

            Raises
            ------
            TypeError
                Provided path increment isn't `float`
            ValueError
                An inappropriate path increment was requested
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: pathIncrement is an float
            if not isinstance(pathIncrement, float):  # pathIncrement is an float
                raise TypeError("`pathIncrement` expects type 'float', received '{}'".format(type(pathIncrement).__name__))

            # ARG CHECK: pathIncrement >= 0
            if not pathIncrement >= 0:
                raise ValueError("`pathIncrement` must be greater than or equal to 0")

            # try and call the function
            try:
                return super().setPathIncrement(pathIncrement)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def toString(self, verbosity: int = 999) -> str:
            """Returns a human-readable string representation of the `GreatCircle`

            Returns a human-readable string representation of the currently-instantiated
            `GreatCircle` object. The amount of information that is to be included
            in the return string is given by the `verbosity` parameter. Each
            `verbosity` level includes all information in preceeding levels.

                0. Nothing, an empty string is returned
                1. Total distance and travel time summary
                2. Gradient correction information for Pn/Sn, nothing for Pg/Lg
                3. Source and receiver `CrustalProfile` information
                4. `Grid` node weights
                5. Head wave interface profiles
                6. Interpolation coefficients for great circle nodes on the head
                   wave interface
                7. Node hit count and node neighbors for every node touched by any
                   `GreatCircle` instantiated by this instance of `SlbmInterface`

            Examples
            --------
                >>> slbm.toString()
                >>> slbm.toString(3)

            Parameters
            ----------
            verbosity : int
                Specifies the amount of information that is to be included in the
                return string. Each verbosity level includes all information in
                preceeding verbosity levels.

            Returns
            -------
            str
                Returns a human-readable string representation of the
                currently-instantiated `GreatCircle` object

            Raises
            ------
            TypeError
                `verbosity` is not an int, or too many arguments were supplied
            ValueError
                An inappropriate `verbosity` value was supplied
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # some error checking
            if not isinstance(verbosity, int):  # verbosity is an int
                raise TypeError("`verbosity` expects type 'int', received '{}'".format(type(verbosity).__name__))

            if verbosity < 0:
                raise ValueError("`verbosity expects a positive integer, received '{}'".format(verbosity))

            # try and call the function
            try:
                return super().toString(verbosity)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e

        def isEqual(self, other: object) -> bool:
            """Compares the model and/or great circle loaded into this and another
            SlbmInteface.

            This is functionally equivalent, and maps, to the overloaded == operator
            which tests whether the model and/or great circle loaded by the current
            instantiation of SlbmInterface is equal to that of another SlbmInterface.

            Examples
            --------
            >>> slbm1 = SlbmInterface()
            >>> slbm2 = SlbmInterface()
            >>> slbm1.loadVelocityModel("example.geotess")
            >>> slbm2.loadVelocityModel("example.geotess")
            >>> slbm1.isEqual(slbm2)
            True
            >>> slbm1.createGreatCircle("Pn", ...)
            >>> slbm2.createGreatCircle("Pg", ...)
            >>> slbm1.isEqual(slbm2)
            False

            Parameters
            ----------
            other : SlbmInterface
                The other SlbmInterface from which to compare its model and great
                circle.

            Returns
            -------
            bool
                Returns whether or not the model and (if applicable) great circle
                attached to the `other` SlbmInterface is equal to the existing one

            Raises
            ------
            TypeError
                Something other than an SlbmInterface was passed to `other`
            RuntimeError
                The RSTT C++ library raised an exception
            """

            # ARG CHECK: argument is another SlbmInterface
            if not isinstance(other, SlbmInterface):
                raise TypeError("`other` expects type 'SlbmInterface', received '{}'".format(type(other).__name__))

            # call operator ==
            return self == other

        # allow calling without instantiating a new SlbmInterface() via rstt.SlbmInterface.modelsEqual()

        @classmethod
        def modelsEqual(self, model_path1: str, model_path2: str) -> bool:
            """Check whether two models are equal

            Examples
            --------
                >>> slbm.modelsEqual("../models/example.geotess", "../models/example.geotess")
                True

                This is also a *classmethod* and can be used without instantiating a
                new SlbmInterface object.

                >>> rstt.SlbmInterface.modelsEqual("../models/example.geotess", "../models/example.geotess")
                True

            Parameters
            ----------
            model_path1 : str
                Path to RSTT model, e.g., `/path/to/modelfile.geotess`. Relative
                path names are accepted.
            model_path2 : str
                Path to RSTT model, e.g., `/path/to/modelfile.geotess`. Relative
                path names are accepted.

            Raises
            ------
            TypeError
                `model_path` is not a `str`, or too many arguments were supplied
            FileNotFoundError
                The specified `model_path` was not found
            RuntimeError
                The RSTT C++ library raised an exception
            Exception
                An unknown exception occurred
            """

            # ARG CHECK: model_path is a str
            if not isinstance(model_path1, str) or not isinstance(model_path2, str):
                raise TypeError("`model_path` expects type 'str', received '{}'".format(type(model_path).__name__))

            # ARG CHECK: model_path exists
            if not os.path.exists(model_path1):
                raise FileNotFoundError("File does not exist: {}".format(model_path1))
            if not os.path.exists(model_path2):
                raise FileNotFoundError("File does not exist: {}".format(model_path2))

            # try and call the function
            try:
                return super().modelsEqual(model_path1, model_path2)

            # catch PyBind and unknown exceptions
            except (RuntimeError, Exception) as e:
                raise e