def full_newton(s, nodes1, t, nodes2):
    r"""Perform a Newton iteration until convergence to a solution.

    This assumes :math:`s` and :math:`t` are sufficiently close to an
    intersection. It **does not** govern the maximum distance away
    that the solution can lie, though the subdivided intervals that contain
    :math:`s` and :math:`t` could be used.

    To avoid round-off issues near ``0.0``, this reverses the direction
    of a curve and replaces the parameter value :math:`\nu` with
    :math:`1 - \nu` whenever :math:`\nu < \tau` (here we use a threshold
    :math:`\tau` equal to :math:`2^{-10}`, i.e. ``ZERO_THRESHOLD``).

    Args:
        s (float): The parameter along the first curve where the iteration
            will start.
        nodes1 (numpy.ndarray): Control points of the first curve.
        t (float): The parameter along the second curve where the iteration
            will start.
        nodes2 (numpy.ndarray): Control points of the second curve.

    Returns:
        Tuple[float, float]: The pair of :math:`s` and :math:`t` values that
        Newton's method converged to.
    """
    if s < ZERO_THRESHOLD:
        reversed1 = np.asfortranarray(nodes1[:, ::-1])
        if t < ZERO_THRESHOLD:
            reversed2 = np.asfortranarray(nodes2[:, ::-1])
            refined_s, refined_t = full_newton_nonzero(
                1.0 - s, reversed1, 1.0 - t, reversed2
            )
            return 1.0 - refined_s, 1.0 - refined_t

        else:
            refined_s, refined_t = full_newton_nonzero(
                1.0 - s, reversed1, t, nodes2
            )
            return 1.0 - refined_s, refined_t

    else:
        if t < ZERO_THRESHOLD:
            reversed2 = np.asfortranarray(nodes2[:, ::-1])
            refined_s, refined_t = full_newton_nonzero(
                s, nodes1, 1.0 - t, reversed2
            )
            return refined_s, 1.0 - refined_t

        else:
            return full_newton_nonzero(s, nodes1, t, nodes2)