#
# Copyright (c) 2008-2012 Stefan Krah. 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.
#
# THIS SOFTWARE IS PROVIDED BY THE AUTHOR 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 AUTHOR 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.
#

#
# Usage: python deccheck.py [--short|--medium|--long|--all]
#


import random
import time

RANDSEED = int(time.time())
random.seed(RANDSEED)

import sys
import os
from copy import copy
from collections import defaultdict

import argparse
import subprocess
from subprocess import PIPE, STDOUT
from queue import Queue, Empty
from threading import Thread, Event, Lock

from test.support.import_helper import import_fresh_module
from randdec import randfloat, all_unary, all_binary, all_ternary
from randdec import unary_optarg, binary_optarg, ternary_optarg
from formathelper import rand_format, rand_locale
from _pydecimal import _dec_from_triple

C = import_fresh_module('decimal', fresh=['_decimal'])
P = import_fresh_module('decimal', blocked=['_decimal'])
EXIT_STATUS = 0


# Contains all categories of Decimal methods.
Functions = {
    # Plain unary:
    'unary': (
        '__abs__', '__bool__', '__ceil__', '__complex__', '__copy__',
        '__floor__', '__float__', '__hash__', '__int__', '__neg__',
        '__pos__', '__reduce__', '__repr__', '__str__', '__trunc__',
        'adjusted', 'as_integer_ratio', 'as_tuple', 'canonical', 'conjugate',
        'copy_abs', 'copy_negate', 'is_canonical', 'is_finite', 'is_infinite',
        'is_nan', 'is_qnan', 'is_signed', 'is_snan', 'is_zero', 'radix'
    ),
    # Unary with optional context:
    'unary_ctx': (
        'exp', 'is_normal', 'is_subnormal', 'ln', 'log10', 'logb',
        'logical_invert', 'next_minus', 'next_plus', 'normalize',
        'number_class', 'sqrt', 'to_eng_string'
    ),
    # Unary with optional rounding mode and context:
    'unary_rnd_ctx': ('to_integral', 'to_integral_exact', 'to_integral_value'),
    # Plain binary:
    'binary': (
        '__add__', '__divmod__', '__eq__', '__floordiv__', '__ge__', '__gt__',
        '__le__', '__lt__', '__mod__', '__mul__', '__ne__', '__pow__',
        '__radd__', '__rdivmod__', '__rfloordiv__', '__rmod__', '__rmul__',
        '__rpow__', '__rsub__', '__rtruediv__', '__sub__', '__truediv__',
        'compare_total', 'compare_total_mag', 'copy_sign', 'quantize',
        'same_quantum'
    ),
    # Binary with optional context:
    'binary_ctx': (
        'compare', 'compare_signal', 'logical_and', 'logical_or', 'logical_xor',
        'max', 'max_mag', 'min', 'min_mag', 'next_toward', 'remainder_near',
        'rotate', 'scaleb', 'shift'
    ),
    # Plain ternary:
    'ternary': ('__pow__',),
    # Ternary with optional context:
    'ternary_ctx': ('fma',),
    # Special:
    'special': ('__format__', '__reduce_ex__', '__round__', 'from_float',
                'quantize'),
    # Properties:
    'property': ('real', 'imag')
}

# Contains all categories of Context methods. The n-ary classification
# applies to the number of Decimal arguments.
ContextFunctions = {
    # Plain nullary:
    'nullary': ('context.__hash__', 'context.__reduce__', 'context.radix'),
    # Plain unary:
    'unary': ('context.abs', 'context.canonical', 'context.copy_abs',
              'context.copy_decimal', 'context.copy_negate',
              'context.create_decimal', 'context.exp', 'context.is_canonical',
              'context.is_finite', 'context.is_infinite', 'context.is_nan',
              'context.is_normal', 'context.is_qnan', 'context.is_signed',
              'context.is_snan', 'context.is_subnormal', 'context.is_zero',
              'context.ln', 'context.log10', 'context.logb',
              'context.logical_invert', 'context.minus', 'context.next_minus',
              'context.next_plus', 'context.normalize', 'context.number_class',
              'context.plus', 'context.sqrt', 'context.to_eng_string',
              'context.to_integral', 'context.to_integral_exact',
              'context.to_integral_value', 'context.to_sci_string'
    ),
    # Plain binary:
    'binary': ('context.add', 'context.compare', 'context.compare_signal',
               'context.compare_total', 'context.compare_total_mag',
               'context.copy_sign', 'context.divide', 'context.divide_int',
               'context.divmod', 'context.logical_and', 'context.logical_or',
               'context.logical_xor', 'context.max', 'context.max_mag',
               'context.min', 'context.min_mag', 'context.multiply',
               'context.next_toward', 'context.power', 'context.quantize',
               'context.remainder', 'context.remainder_near', 'context.rotate',
               'context.same_quantum', 'context.scaleb', 'context.shift',
               'context.subtract'
    ),
    # Plain ternary:
    'ternary': ('context.fma', 'context.power'),
    # Special:
    'special': ('context.__reduce_ex__', 'context.create_decimal_from_float')
}

# Functions that set no context flags but whose result can differ depending
# on prec, Emin and Emax.
MaxContextSkip = ['is_normal', 'is_subnormal', 'logical_invert', 'next_minus',
                  'next_plus', 'number_class', 'logical_and', 'logical_or',
                  'logical_xor', 'next_toward', 'rotate', 'shift']

# Functions that require a restricted exponent range for reasonable runtimes.
UnaryRestricted = [
  '__ceil__', '__floor__', '__int__', '__trunc__',
  'as_integer_ratio', 'to_integral', 'to_integral_value'
]

BinaryRestricted = ['__round__']

TernaryRestricted = ['__pow__', 'context.power']


# ======================================================================
#                            Unified Context
# ======================================================================

# Translate symbols.
CondMap = {
        C.Clamped:             P.Clamped,
        C.ConversionSyntax:    P.ConversionSyntax,
        C.DivisionByZero:      P.DivisionByZero,
        C.DivisionImpossible:  P.InvalidOperation,
        C.DivisionUndefined:   P.DivisionUndefined,
        C.Inexact:             P.Inexact,
        C.InvalidContext:      P.InvalidContext,
        C.InvalidOperation:    P.InvalidOperation,
        C.Overflow:            P.Overflow,
        C.Rounded:             P.Rounded,
        C.Subnormal:           P.Subnormal,
        C.Underflow:           P.Underflow,
        C.FloatOperation:      P.FloatOperation,
}

RoundModes = [C.ROUND_UP, C.ROUND_DOWN, C.ROUND_CEILING, C.ROUND_FLOOR,
              C.ROUND_HALF_UP, C.ROUND_HALF_DOWN, C.ROUND_HALF_EVEN,
              C.ROUND_05UP]


class Context(object):
    """Provides a convenient way of syncing the C and P contexts"""

    __slots__ = ['c', 'p']

    def __init__(self, c_ctx=None, p_ctx=None):
        """Initialization is from the C context"""
        self.c = C.getcontext() if c_ctx is None else c_ctx
        self.p = P.getcontext() if p_ctx is None else p_ctx
        self.p.prec = self.c.prec
        self.p.Emin = self.c.Emin
        self.p.Emax = self.c.Emax
        self.p.rounding = self.c.rounding
        self.p.capitals = self.c.capitals
        self.settraps([sig for sig in self.c.traps if self.c.traps[sig]])
        self.setstatus([sig for sig in self.c.flags if self.c.flags[sig]])
        self.p.clamp = self.c.clamp

    def __str__(self):
        return str(self.c) + '\n' + str(self.p)

    def getprec(self):
        assert(self.c.prec == self.p.prec)
        return self.c.prec

    def setprec(self, val):
        self.c.prec = val
        self.p.prec = val

    def getemin(self):
        assert(self.c.Emin == self.p.Emin)
        return self.c.Emin

    def setemin(self, val):
        self.c.Emin = val
        self.p.Emin = val

    def getemax(self):
        assert(self.c.Emax == self.p.Emax)
        return self.c.Emax

    def setemax(self, val):
        self.c.Emax = val
        self.p.Emax = val

    def getround(self):
        assert(self.c.rounding == self.p.rounding)
        return self.c.rounding

    def setround(self, val):
        self.c.rounding = val
        self.p.rounding = val

    def getcapitals(self):
        assert(self.c.capitals == self.p.capitals)
        return self.c.capitals

    def setcapitals(self, val):
        self.c.capitals = val
        self.p.capitals = val

    def getclamp(self):
        assert(self.c.clamp == self.p.clamp)
        return self.c.clamp

    def setclamp(self, val):
        self.c.clamp = val
        self.p.clamp = val

    prec = property(getprec, setprec)
    Emin = property(getemin, setemin)
    Emax = property(getemax, setemax)
    rounding = property(getround, setround)
    clamp = property(getclamp, setclamp)
    capitals = property(getcapitals, setcapitals)

    def clear_traps(self):
        self.c.clear_traps()
        for trap in self.p.traps:
            self.p.traps[trap] = False

    def clear_status(self):
        self.c.clear_flags()
        self.p.clear_flags()

    def settraps(self, lst):
        """lst: C signal list"""
        self.clear_traps()
        for signal in lst:
            self.c.traps[signal] = True
            self.p.traps[CondMap[signal]] = True

    def setstatus(self, lst):
        """lst: C signal list"""
        self.clear_status()
        for signal in lst:
            self.c.flags[signal] = True
            self.p.flags[CondMap[signal]] = True

    def assert_eq_status(self):
        """assert equality of C and P status"""
        for signal in self.c.flags:
            if self.c.flags[signal] == (not self.p.flags[CondMap[signal]]):
                return False
        return True


# We don't want exceptions so that we can compare the status flags.
context = Context()
context.Emin = C.MIN_EMIN
context.Emax = C.MAX_EMAX
context.clear_traps()

# When creating decimals, _decimal is ultimately limited by the maximum
# context values. We emulate this restriction for decimal.py.
maxcontext = P.Context(
    prec=C.MAX_PREC,
    Emin=C.MIN_EMIN,
    Emax=C.MAX_EMAX,
    rounding=P.ROUND_HALF_UP,
    capitals=1
)
maxcontext.clamp = 0

def RestrictedDecimal(value):
    maxcontext.traps = copy(context.p.traps)
    maxcontext.clear_flags()
    if isinstance(value, str):
        value = value.strip()
    dec = maxcontext.create_decimal(value)
    if maxcontext.flags[P.Inexact] or \
       maxcontext.flags[P.Rounded] or \
       maxcontext.flags[P.Clamped] or \
       maxcontext.flags[P.InvalidOperation]:
        return context.p._raise_error(P.InvalidOperation)
    if maxcontext.flags[P.FloatOperation]:
        context.p.flags[P.FloatOperation] = True
    return dec


# ======================================================================
#      TestSet: Organize data and events during a single test case
# ======================================================================

class RestrictedList(list):
    """List that can only be modified by appending items."""
    def __getattribute__(self, name):
        if name != 'append':
            raise AttributeError("unsupported operation")
        return list.__getattribute__(self, name)
    def unsupported(self, *_):
        raise AttributeError("unsupported operation")
    __add__ = __delattr__ = __delitem__ = __iadd__ = __imul__ = unsupported
    __mul__ = __reversed__ = __rmul__ = __setattr__ = __setitem__ = unsupported

class TestSet(object):
    """A TestSet contains the original input operands, converted operands,
       Python exceptions that occurred either during conversion or during
       execution of the actual function, and the final results.

       For safety, most attributes are lists that only support the append
       operation.

       If a function name is prefixed with 'context.', the corresponding
       context method is called.
    """
    def __init__(self, funcname, operands):
        if funcname.startswith("context."):
            self.funcname = funcname.replace("context.", "")
            self.contextfunc = True
        else:
            self.funcname = funcname
            self.contextfunc = False
        self.op = operands               # raw operand tuple
        self.context = context           # context used for the operation
        self.cop = RestrictedList()      # converted C.Decimal operands
        self.cex = RestrictedList()      # Python exceptions for C.Decimal
        self.cresults = RestrictedList() # C.Decimal results
        self.pop = RestrictedList()      # converted P.Decimal operands
        self.pex = RestrictedList()      # Python exceptions for P.Decimal
        self.presults = RestrictedList() # P.Decimal results

        # If the above results are exact, unrounded and not clamped, repeat
        # the operation with a maxcontext to ensure that huge intermediate
        # values do not cause a MemoryError.
        self.with_maxcontext = False
        self.maxcontext = context.c.copy()
        self.maxcontext.prec = C.MAX_PREC
        self.maxcontext.Emax = C.MAX_EMAX
        self.maxcontext.Emin = C.MIN_EMIN
        self.maxcontext.clear_flags()

        self.maxop = RestrictedList()       # converted C.Decimal operands
        self.maxex = RestrictedList()       # Python exceptions for C.Decimal
        self.maxresults = RestrictedList()  # C.Decimal results


# ======================================================================
#                SkipHandler: skip known discrepancies
# ======================================================================

class SkipHandler:
    """Handle known discrepancies between decimal.py and _decimal.so.
       These are either ULP differences in the power function or
       extremely minor issues."""

    def __init__(self):
        self.ulpdiff = 0
        self.powmod_zeros = 0
        self.maxctx = P.Context(Emax=10**18, Emin=-10**18)

    def default(self, t):
        return False
    __ge__ =  __gt__ = __le__ = __lt__ = __ne__ = __eq__ = default
    __reduce__ = __format__ = __repr__ = __str__ = default

    def harrison_ulp(self, dec):
        """ftp://ftp.inria.fr/INRIA/publication/publi-pdf/RR/RR-5504.pdf"""
        a = dec.next_plus()
        b = dec.next_minus()
        return abs(a - b)

    def standard_ulp(self, dec, prec):
        return _dec_from_triple(0, '1', dec._exp+len(dec._int)-prec)

    def rounding_direction(self, x, mode):
        """Determine the effective direction of the rounding when
           the exact result x is rounded according to mode.
           Return -1 for downwards, 0 for undirected, 1 for upwards,
           2 for ROUND_05UP."""
        cmp = 1 if x.compare_total(P.Decimal("+0")) >= 0 else -1

        if mode in (P.ROUND_HALF_EVEN, P.ROUND_HALF_UP, P.ROUND_HALF_DOWN):
            return 0
        elif mode == P.ROUND_CEILING:
            return 1
        elif mode == P.ROUND_FLOOR:
            return -1
        elif mode == P.ROUND_UP:
            return cmp
        elif mode == P.ROUND_DOWN:
            return -cmp
        elif mode == P.ROUND_05UP:
            return 2
        else:
            raise ValueError("Unexpected rounding mode: %s" % mode)

    def check_ulpdiff(self, exact, rounded):
        # current precision
        p = context.p.prec

        # Convert infinities to the largest representable number + 1.
        x = exact
        if exact.is_infinite():
            x = _dec_from_triple(exact._sign, '10', context.p.Emax)
        y = rounded
        if rounded.is_infinite():
            y = _dec_from_triple(rounded._sign, '10', context.p.Emax)

        # err = (rounded - exact) / ulp(rounded)
        self.maxctx.prec = p * 2
        t = self.maxctx.subtract(y, x)
        if context.c.flags[C.Clamped] or \
           context.c.flags[C.Underflow]:
            # The standard ulp does not work in Underflow territory.
            ulp = self.harrison_ulp(y)
        else:
            ulp = self.standard_ulp(y, p)
        # Error in ulps.
        err = self.maxctx.divide(t, ulp)

        dir = self.rounding_direction(x, context.p.rounding)
        if dir == 0:
            if P.Decimal("-0.6") < err < P.Decimal("0.6"):
                return True
        elif dir == 1: # directed, upwards
            if P.Decimal("-0.1") < err < P.Decimal("1.1"):
                return True
        elif dir == -1: # directed, downwards
            if P.Decimal("-1.1") < err < P.Decimal("0.1"):
                return True
        else: # ROUND_05UP
            if P.Decimal("-1.1") < err < P.Decimal("1.1"):
                return True

        print("ulp: %s  error: %s  exact: %s  c_rounded: %s"
              % (ulp, err, exact, rounded))
        return False

    def bin_resolve_ulp(self, t):
        """Check if results of _decimal's power function are within the
           allowed ulp ranges."""
        # NaNs are beyond repair.
        if t.rc.is_nan() or t.rp.is_nan():
            return False

        # "exact" result, double precision, half_even
        self.maxctx.prec = context.p.prec * 2

        op1, op2 = t.pop[0], t.pop[1]
        if t.contextfunc:
            exact = getattr(self.maxctx, t.funcname)(op1, op2)
        else:
            exact = getattr(op1, t.funcname)(op2, context=self.maxctx)

        # _decimal's rounded result
        rounded = P.Decimal(t.cresults[0])

        self.ulpdiff += 1
        return self.check_ulpdiff(exact, rounded)

    ############################ Correct rounding #############################
    def resolve_underflow(self, t):
        """In extremely rare cases where the infinite precision result is just
           below etiny, cdecimal does not set Subnormal/Underflow. Example:

           setcontext(Context(prec=21, rounding=ROUND_UP, Emin=-55, Emax=85))
           Decimal("1.00000000000000000000000000000000000000000000000"
                   "0000000100000000000000000000000000000000000000000"
                   "0000000000000025").ln()
        """
        if t.cresults != t.presults:
            return False # Results must be identical.
        if context.c.flags[C.Rounded] and \
           context.c.flags[C.Inexact] and \
           context.p.flags[P.Rounded] and \
           context.p.flags[P.Inexact]:
            return True # Subnormal/Underflow may be missing.
        return False

    def exp(self, t):
        """Resolve Underflow or ULP difference."""
        return self.resolve_underflow(t)

    def log10(self, t):
        """Resolve Underflow or ULP difference."""
        return self.resolve_underflow(t)

    def ln(self, t):
        """Resolve Underflow or ULP difference."""
        return self.resolve_underflow(t)

    def __pow__(self, t):
        """Always calls the resolve function. C.Decimal does not have correct
           rounding for the power function."""
        if context.c.flags[C.Rounded] and \
           context.c.flags[C.Inexact] and \
           context.p.flags[P.Rounded] and \
           context.p.flags[P.Inexact]:
            return self.bin_resolve_ulp(t)
        else:
            return False
    power = __rpow__ = __pow__

    ############################## Technicalities #############################
    def __float__(self, t):
        """NaN comparison in the verify() function obviously gives an
           incorrect answer:  nan == nan -> False"""
        if t.cop[0].is_nan() and t.pop[0].is_nan():
            return True
        return False
    __complex__ = __float__

    def __radd__(self, t):
        """decimal.py gives precedence to the first NaN; this is
           not important, as __radd__ will not be called for
           two decimal arguments."""
        if t.rc.is_nan() and t.rp.is_nan():
            return True
        return False
    __rmul__ = __radd__

    ################################ Various ##################################
    def __round__(self, t):
        """Exception: Decimal('1').__round__(-100000000000000000000000000)
           Should it really be InvalidOperation?"""
        if t.rc is None and t.rp.is_nan():
            return True
        return False

shandler = SkipHandler()
def skip_error(t):
    return getattr(shandler, t.funcname, shandler.default)(t)


# ======================================================================
#                      Handling verification errors
# ======================================================================

class VerifyError(Exception):
    """Verification failed."""
    pass

def function_as_string(t):
    if t.contextfunc:
        cargs = t.cop
        pargs = t.pop
        maxargs = t.maxop
        cfunc = "c_func: %s(" % t.funcname
        pfunc = "p_func: %s(" % t.funcname
        maxfunc = "max_func: %s(" % t.funcname
    else:
        cself, cargs = t.cop[0], t.cop[1:]
        pself, pargs = t.pop[0], t.pop[1:]
        maxself, maxargs = t.maxop[0], t.maxop[1:]
        cfunc = "c_func: %s.%s(" % (repr(cself), t.funcname)
        pfunc = "p_func: %s.%s(" % (repr(pself), t.funcname)
        maxfunc = "max_func: %s.%s(" % (repr(maxself), t.funcname)

    err = cfunc
    for arg in cargs:
        err += "%s, " % repr(arg)
    err = err.rstrip(", ")
    err += ")\n"

    err += pfunc
    for arg in pargs:
        err += "%s, " % repr(arg)
    err = err.rstrip(", ")
    err += ")"

    if t.with_maxcontext:
        err += "\n"
        err += maxfunc
        for arg in maxargs:
            err += "%s, " % repr(arg)
        err = err.rstrip(", ")
        err += ")"

    return err

def raise_error(t):
    global EXIT_STATUS

    if skip_error(t):
        return
    EXIT_STATUS = 1

    err = "Error in %s:\n\n" % t.funcname
    err += "input operands: %s\n\n" % (t.op,)
    err += function_as_string(t)

    err += "\n\nc_result: %s\np_result: %s\n" % (t.cresults, t.presults)
    if t.with_maxcontext:
        err += "max_result: %s\n\n" % (t.maxresults)
    else:
        err += "\n"

    err += "c_exceptions: %s\np_exceptions: %s\n" % (t.cex, t.pex)
    if t.with_maxcontext:
        err += "max_exceptions: %s\n\n" % t.maxex
    else:
        err += "\n"

    err += "%s\n" % str(t.context)
    if t.with_maxcontext:
        err += "%s\n" % str(t.maxcontext)
    else:
        err += "\n"

    raise VerifyError(err)


# ======================================================================
#                        Main testing functions
#
#  The procedure is always (t is the TestSet):
#
#   convert(t) -> Initialize the TestSet as necessary.
#
#                 Return 0 for early abortion (e.g. if a TypeError
#                 occurs during conversion, there is nothing to test).
#
#                 Return 1 for continuing with the test case.
#
#   callfuncs(t) -> Call the relevant function for each implementation
#                   and record the results in the TestSet.
#
#   verify(t) -> Verify the results. If verification fails, details
#                are printed to stdout.
# ======================================================================

def all_nan(a):
    if isinstance(a, C.Decimal):
        return a.is_nan()
    elif isinstance(a, tuple):
        return all(all_nan(v) for v in a)
    return False

def convert(t, convstr=True):
    """ t is the testset. At this stage the testset contains a tuple of
        operands t.op of various types. For decimal methods the first
        operand (self) is always converted to Decimal. If 'convstr' is
        true, string operands are converted as well.

        Context operands are of type deccheck.Context, rounding mode
        operands are given as a tuple (C.rounding, P.rounding).

        Other types (float, int, etc.) are left unchanged.
    """
    for i, op in enumerate(t.op):

        context.clear_status()
        t.maxcontext.clear_flags()

        if op in RoundModes:
            t.cop.append(op)
            t.pop.append(op)
            t.maxop.append(op)

        elif not t.contextfunc and i == 0 or \
             convstr and isinstance(op, str):
            try:
                c = C.Decimal(op)
                cex = None
            except (TypeError, ValueError, OverflowError) as e:
                c = None
                cex = e.__class__

            try:
                p = RestrictedDecimal(op)
                pex = None
            except (TypeError, ValueError, OverflowError) as e:
                p = None
                pex = e.__class__

            try:
                C.setcontext(t.maxcontext)
                maxop = C.Decimal(op)
                maxex = None
            except (TypeError, ValueError, OverflowError) as e:
                maxop = None
                maxex = e.__class__
            finally:
                C.setcontext(context.c)

            t.cop.append(c)
            t.cex.append(cex)

            t.pop.append(p)
            t.pex.append(pex)

            t.maxop.append(maxop)
            t.maxex.append(maxex)

            if cex is pex:
                if str(c) != str(p) or not context.assert_eq_status():
                    raise_error(t)
                if cex and pex:
                    # nothing to test
                    return 0
            else:
                raise_error(t)

            # The exceptions in the maxcontext operation can legitimately
            # differ, only test that maxex implies cex:
            if maxex is not None and cex is not maxex:
                raise_error(t)

        elif isinstance(op, Context):
            t.context = op
            t.cop.append(op.c)
            t.pop.append(op.p)
            t.maxop.append(t.maxcontext)

        else:
            t.cop.append(op)
            t.pop.append(op)
            t.maxop.append(op)

    return 1

def callfuncs(t):
    """ t is the testset. At this stage the testset contains operand lists
        t.cop and t.pop for the C and Python versions of decimal.
        For Decimal methods, the first operands are of type C.Decimal and
        P.Decimal respectively. The remaining operands can have various types.
        For Context methods, all operands can have any type.

        t.rc and t.rp are the results of the operation.
    """
    context.clear_status()
    t.maxcontext.clear_flags()

    try:
        if t.contextfunc:
            cargs = t.cop
            t.rc = getattr(context.c, t.funcname)(*cargs)
        else:
            cself = t.cop[0]
            cargs = t.cop[1:]
            t.rc = getattr(cself, t.funcname)(*cargs)
        t.cex.append(None)
    except (TypeError, ValueError, OverflowError, MemoryError) as e:
        t.rc = None
        t.cex.append(e.__class__)

    try:
        if t.contextfunc:
            pargs = t.pop
            t.rp = getattr(context.p, t.funcname)(*pargs)
        else:
            pself = t.pop[0]
            pargs = t.pop[1:]
            t.rp = getattr(pself, t.funcname)(*pargs)
        t.pex.append(None)
    except (TypeError, ValueError, OverflowError, MemoryError) as e:
        t.rp = None
        t.pex.append(e.__class__)

    # If the above results are exact, unrounded, normal etc., repeat the
    # operation with a maxcontext to ensure that huge intermediate values
    # do not cause a MemoryError.
    if (t.funcname not in MaxContextSkip and
        not context.c.flags[C.InvalidOperation] and
        not context.c.flags[C.Inexact] and
        not context.c.flags[C.Rounded] and
        not context.c.flags[C.Subnormal] and
        not context.c.flags[C.Clamped] and
        not context.clamp and # results are padded to context.prec if context.clamp==1.
        not any(isinstance(v, C.Context) for v in t.cop)): # another context is used.
        t.with_maxcontext = True
        try:
            if t.contextfunc:
                maxargs = t.maxop
                t.rmax = getattr(t.maxcontext, t.funcname)(*maxargs)
            else:
                maxself = t.maxop[0]
                maxargs = t.maxop[1:]
                try:
                    C.setcontext(t.maxcontext)
                    t.rmax = getattr(maxself, t.funcname)(*maxargs)
                finally:
                    C.setcontext(context.c)
            t.maxex.append(None)
        except (TypeError, ValueError, OverflowError, MemoryError) as e:
            t.rmax = None
            t.maxex.append(e.__class__)

def verify(t, stat):
    """ t is the testset. At this stage the testset contains the following
        tuples:

            t.op: original operands
            t.cop: C.Decimal operands (see convert for details)
            t.pop: P.Decimal operands (see convert for details)
            t.rc: C result
            t.rp: Python result

        t.rc and t.rp can have various types.
    """
    t.cresults.append(str(t.rc))
    t.presults.append(str(t.rp))
    if t.with_maxcontext:
        t.maxresults.append(str(t.rmax))

    if isinstance(t.rc, C.Decimal) and isinstance(t.rp, P.Decimal):
        # General case: both results are Decimals.
        t.cresults.append(t.rc.to_eng_string())
        t.cresults.append(t.rc.as_tuple())
        t.cresults.append(str(t.rc.imag))
        t.cresults.append(str(t.rc.real))
        t.presults.append(t.rp.to_eng_string())
        t.presults.append(t.rp.as_tuple())
        t.presults.append(str(t.rp.imag))
        t.presults.append(str(t.rp.real))

        if t.with_maxcontext and isinstance(t.rmax, C.Decimal):
            t.maxresults.append(t.rmax.to_eng_string())
            t.maxresults.append(t.rmax.as_tuple())
            t.maxresults.append(str(t.rmax.imag))
            t.maxresults.append(str(t.rmax.real))

        nc = t.rc.number_class().lstrip('+-s')
        stat[nc] += 1
    else:
        # Results from e.g. __divmod__ can only be compared as strings.
        if not isinstance(t.rc, tuple) and not isinstance(t.rp, tuple):
            if t.rc != t.rp:
                raise_error(t)
            if t.with_maxcontext and not isinstance(t.rmax, tuple):
                if t.rmax != t.rc:
                    raise_error(t)
        stat[type(t.rc).__name__] += 1

    # The return value lists must be equal.
    if t.cresults != t.presults:
        raise_error(t)
    # The Python exception lists (TypeError, etc.) must be equal.
    if t.cex != t.pex:
        raise_error(t)
    # The context flags must be equal.
    if not t.context.assert_eq_status():
        raise_error(t)

    if t.with_maxcontext:
        # NaN payloads etc. depend on precision and clamp.
        if all_nan(t.rc) and all_nan(t.rmax):
            return
        # The return value lists must be equal.
        if t.maxresults != t.cresults:
            raise_error(t)
        # The Python exception lists (TypeError, etc.) must be equal.
        if t.maxex != t.cex:
            raise_error(t)
        # The context flags must be equal.
        if t.maxcontext.flags != t.context.c.flags:
            raise_error(t)


# ======================================================================
#                           Main test loops
#
#  test_method(method, testspecs, testfunc) ->
#
#     Loop through various context settings. The degree of
#     thoroughness is determined by 'testspec'. For each
#     setting, call 'testfunc'. Generally, 'testfunc' itself
#     a loop, iterating through many test cases generated
#     by the functions in randdec.py.
#
#  test_n-ary(method, prec, exp_range, restricted_range, itr, stat) ->
#
#     'test_unary', 'test_binary' and 'test_ternary' are the
#     main test functions passed to 'test_method'. They deal
#     with the regular cases. The thoroughness of testing is
#     determined by 'itr'.
#
#     'prec', 'exp_range' and 'restricted_range' are passed
#     to the test-generating functions and limit the generated
#     values. In some cases, for reasonable run times a
#     maximum exponent of 9999 is required.
#
#     The 'stat' parameter is passed down to the 'verify'
#     function, which records statistics for the result values.
# ======================================================================

def log(fmt, args=None):
    if args:
        sys.stdout.write(''.join((fmt, '\n')) % args)
    else:
        sys.stdout.write(''.join((str(fmt), '\n')))
    sys.stdout.flush()

def test_method(method, testspecs, testfunc):
    """Iterate a test function through many context settings."""
    log("testing %s ...", method)
    stat = defaultdict(int)
    for spec in testspecs:
        if 'samples' in spec:
            spec['prec'] = sorted(random.sample(range(1, 101),
                                  spec['samples']))
        for prec in spec['prec']:
            context.prec = prec
            for expts in spec['expts']:
                emin, emax = expts
                if emin == 'rand':
                    context.Emin = random.randrange(-1000, 0)
                    context.Emax = random.randrange(prec, 1000)
                else:
                    context.Emin, context.Emax = emin, emax
                if prec > context.Emax: continue
                log("    prec: %d  emin: %d  emax: %d",
                    (context.prec, context.Emin, context.Emax))
                restr_range = 9999 if context.Emax > 9999 else context.Emax+99
                for rounding in RoundModes:
                    context.rounding = rounding
                    context.capitals = random.randrange(2)
                    if spec['clamp'] == 'rand':
                        context.clamp = random.randrange(2)
                    else:
                        context.clamp = spec['clamp']
                    exprange = context.c.Emax
                    testfunc(method, prec, exprange, restr_range,
                             spec['iter'], stat)
    log("    result types: %s" % sorted([t for t in stat.items()]))

def test_unary(method, prec, exp_range, restricted_range, itr, stat):
    """Iterate a unary function through many test cases."""
    if method in UnaryRestricted:
        exp_range = restricted_range
    for op in all_unary(prec, exp_range, itr):
        t = TestSet(method, op)
        try:
            if not convert(t):
                continue
            callfuncs(t)
            verify(t, stat)
        except VerifyError as err:
            log(err)

    if not method.startswith('__'):
        for op in unary_optarg(prec, exp_range, itr):
            t = TestSet(method, op)
            try:
                if not convert(t):
                    continue
                callfuncs(t)
                verify(t, stat)
            except VerifyError as err:
                log(err)

def test_binary(method, prec, exp_range, restricted_range, itr, stat):
    """Iterate a binary function through many test cases."""
    if method in BinaryRestricted:
        exp_range = restricted_range
    for op in all_binary(prec, exp_range, itr):
        t = TestSet(method, op)
        try:
            if not convert(t):
                continue
            callfuncs(t)
            verify(t, stat)
        except VerifyError as err:
            log(err)

    if not method.startswith('__'):
        for op in binary_optarg(prec, exp_range, itr):
            t = TestSet(method, op)
            try:
                if not convert(t):
                    continue
                callfuncs(t)
                verify(t, stat)
            except VerifyError as err:
                log(err)

def test_ternary(method, prec, exp_range, restricted_range, itr, stat):
    """Iterate a ternary function through many test cases."""
    if method in TernaryRestricted:
        exp_range = restricted_range
    for op in all_ternary(prec, exp_range, itr):
        t = TestSet(method, op)
        try:
            if not convert(t):
                continue
            callfuncs(t)
            verify(t, stat)
        except VerifyError as err:
            log(err)

    if not method.startswith('__'):
        for op in ternary_optarg(prec, exp_range, itr):
            t = TestSet(method, op)
            try:
                if not convert(t):
                    continue
                callfuncs(t)
                verify(t, stat)
            except VerifyError as err:
                log(err)

def test_format(method, prec, exp_range, restricted_range, itr, stat):
    """Iterate the __format__ method through many test cases."""
    for op in all_unary(prec, exp_range, itr):
        fmt1 = rand_format(chr(random.randrange(0, 128)), 'EeGgn')
        fmt2 = rand_locale()
        for fmt in (fmt1, fmt2):
            fmtop = (op[0], fmt)
            t = TestSet(method, fmtop)
            try:
                if not convert(t, convstr=False):
                    continue
                callfuncs(t)
                verify(t, stat)
            except VerifyError as err:
                log(err)
    for op in all_unary(prec, 9999, itr):
        fmt1 = rand_format(chr(random.randrange(0, 128)), 'Ff%')
        fmt2 = rand_locale()
        for fmt in (fmt1, fmt2):
            fmtop = (op[0], fmt)
            t = TestSet(method, fmtop)
            try:
                if not convert(t, convstr=False):
                    continue
                callfuncs(t)
                verify(t, stat)
            except VerifyError as err:
                log(err)

def test_round(method, prec, exprange, restricted_range, itr, stat):
    """Iterate the __round__ method through many test cases."""
    for op in all_unary(prec, 9999, itr):
        n = random.randrange(10)
        roundop = (op[0], n)
        t = TestSet(method, roundop)
        try:
            if not convert(t):
                continue
            callfuncs(t)
            verify(t, stat)
        except VerifyError as err:
            log(err)

def test_from_float(method, prec, exprange, restricted_range, itr, stat):
    """Iterate the __float__ method through many test cases."""
    for rounding in RoundModes:
        context.rounding = rounding
        for i in range(1000):
            f = randfloat()
            op = (f,) if method.startswith("context.") else ("sNaN", f)
            t = TestSet(method, op)
            try:
                if not convert(t):
                    continue
                callfuncs(t)
                verify(t, stat)
            except VerifyError as err:
                log(err)

def randcontext(exprange):
    c = Context(C.Context(), P.Context())
    c.Emax = random.randrange(1, exprange+1)
    c.Emin = random.randrange(-exprange, 0)
    maxprec = 100 if c.Emax >= 100 else c.Emax
    c.prec = random.randrange(1, maxprec+1)
    c.clamp = random.randrange(2)
    c.clear_traps()
    return c

def test_quantize_api(method, prec, exprange, restricted_range, itr, stat):
    """Iterate the 'quantize' method through many test cases, using
       the optional arguments."""
    for op in all_binary(prec, restricted_range, itr):
        for rounding in RoundModes:
            c = randcontext(exprange)
            quantizeop = (op[0], op[1], rounding, c)
            t = TestSet(method, quantizeop)
            try:
                if not convert(t):
                    continue
                callfuncs(t)
                verify(t, stat)
            except VerifyError as err:
                log(err)


def check_untested(funcdict, c_cls, p_cls):
    """Determine untested, C-only and Python-only attributes.
       Uncomment print lines for debugging."""
    c_attr = set(dir(c_cls))
    p_attr = set(dir(p_cls))
    intersect = c_attr & p_attr

    funcdict['c_only'] = tuple(sorted(c_attr-intersect))
    funcdict['p_only'] = tuple(sorted(p_attr-intersect))

    tested = set()
    for lst in funcdict.values():
        for v in lst:
            v = v.replace("context.", "") if c_cls == C.Context else v
            tested.add(v)

    funcdict['untested'] = tuple(sorted(intersect-tested))

    # for key in ('untested', 'c_only', 'p_only'):
    #     s = 'Context' if c_cls == C.Context else 'Decimal'
    #     print("\n%s %s:\n%s" % (s, key, funcdict[key]))


if __name__ == '__main__':

    parser = argparse.ArgumentParser(prog="deccheck.py")

    group = parser.add_mutually_exclusive_group()
    group.add_argument('--short', dest='time', action="store_const", const='short', default='short', help="short test (default)")
    group.add_argument('--medium', dest='time', action="store_const", const='medium', default='short', help="medium test (reasonable run time)")
    group.add_argument('--long', dest='time', action="store_const", const='long', default='short', help="long test (long run time)")
    group.add_argument('--all', dest='time', action="store_const", const='all', default='short', help="all tests (excessive run time)")

    group = parser.add_mutually_exclusive_group()
    group.add_argument('--single', dest='single', nargs=1, default=False, metavar="TEST", help="run a single test")
    group.add_argument('--multicore', dest='multicore', action="store_true", default=False, help="use all available cores")

    args = parser.parse_args()
    assert args.single is False or args.multicore is False
    if args.single:
        args.single = args.single[0]


    # Set up the testspecs list. A testspec is simply a dictionary
    # that determines the amount of different contexts that 'test_method'
    # will generate.
    base_expts = [(C.MIN_EMIN, C.MAX_EMAX)]
    if C.MAX_EMAX == 999999999999999999:
        base_expts.append((-999999999, 999999999))

    # Basic contexts.
    base = {
        'expts': base_expts,
        'prec': [],
        'clamp': 'rand',
        'iter': None,
        'samples': None,
    }
    # Contexts with small values for prec, emin, emax.
    small = {
        'prec': [1, 2, 3, 4, 5],
        'expts': [(-1, 1), (-2, 2), (-3, 3), (-4, 4), (-5, 5)],
        'clamp': 'rand',
        'iter': None
    }
    # IEEE interchange format.
    ieee = [
        # DECIMAL32
        {'prec': [7], 'expts': [(-95, 96)], 'clamp': 1, 'iter': None},
        # DECIMAL64
        {'prec': [16], 'expts': [(-383, 384)], 'clamp': 1, 'iter': None},
        # DECIMAL128
        {'prec': [34], 'expts': [(-6143, 6144)], 'clamp': 1, 'iter': None}
    ]

    if args.time == 'medium':
        base['expts'].append(('rand', 'rand'))
        # 5 random precisions
        base['samples'] = 5
        testspecs = [small] + ieee + [base]
    elif args.time == 'long':
        base['expts'].append(('rand', 'rand'))
        # 10 random precisions
        base['samples'] = 10
        testspecs = [small] + ieee + [base]
    elif args.time == 'all':
        base['expts'].append(('rand', 'rand'))
        # All precisions in [1, 100]
        base['samples'] = 100
        testspecs = [small] + ieee + [base]
    else: # --short
        rand_ieee = random.choice(ieee)
        base['iter'] = small['iter'] = rand_ieee['iter'] = 1
        # 1 random precision and exponent pair
        base['samples'] = 1
        base['expts'] = [random.choice(base_expts)]
        # 1 random precision and exponent pair
        prec = random.randrange(1, 6)
        small['prec'] = [prec]
        small['expts'] = [(-prec, prec)]
        testspecs = [small, rand_ieee, base]


    check_untested(Functions, C.Decimal, P.Decimal)
    check_untested(ContextFunctions, C.Context, P.Context)


    if args.multicore:
        q = Queue()
    elif args.single:
        log("Random seed: %d", RANDSEED)
    else:
        log("\n\nRandom seed: %d\n\n", RANDSEED)


    FOUND_METHOD = False
    def do_single(method, f):
        global FOUND_METHOD
        if args.multicore:
            q.put(method)
        elif not args.single or args.single == method:
            FOUND_METHOD = True
            f()

    # Decimal methods:
    for method in Functions['unary'] + Functions['unary_ctx'] + \
                  Functions['unary_rnd_ctx']:
        do_single(method, lambda: test_method(method, testspecs, test_unary))

    for method in Functions['binary'] + Functions['binary_ctx']:
        do_single(method, lambda: test_method(method, testspecs, test_binary))

    for method in Functions['ternary'] + Functions['ternary_ctx']:
        name = '__powmod__' if method == '__pow__' else method
        do_single(name, lambda: test_method(method, testspecs, test_ternary))

    do_single('__format__', lambda: test_method('__format__', testspecs, test_format))
    do_single('__round__', lambda: test_method('__round__', testspecs, test_round))
    do_single('from_float', lambda: test_method('from_float', testspecs, test_from_float))
    do_single('quantize_api', lambda: test_method('quantize', testspecs, test_quantize_api))

    # Context methods:
    for method in ContextFunctions['unary']:
        do_single(method, lambda: test_method(method, testspecs, test_unary))

    for method in ContextFunctions['binary']:
        do_single(method, lambda: test_method(method, testspecs, test_binary))

    for method in ContextFunctions['ternary']:
        name = 'context.powmod' if method == 'context.power' else method
        do_single(name, lambda: test_method(method, testspecs, test_ternary))

    do_single('context.create_decimal_from_float',
              lambda: test_method('context.create_decimal_from_float',
                                   testspecs, test_from_float))

    if args.multicore:
        error = Event()
        write_lock = Lock()

        def write_output(out, returncode):
            if returncode != 0:
                error.set()

            with write_lock:
                sys.stdout.buffer.write(out + b"\n")
                sys.stdout.buffer.flush()

        def tfunc():
            while not error.is_set():
                try:
                    test = q.get(block=False, timeout=-1)
                except Empty:
                    return

                cmd = [sys.executable, "deccheck.py", "--%s" % args.time, "--single", test]
                p = subprocess.Popen(cmd, stdout=PIPE, stderr=STDOUT)
                out, _ = p.communicate()
                write_output(out, p.returncode)

        N = os.process_cpu_count()
        t = N * [None]

        for i in range(N):
            t[i] = Thread(target=tfunc)
            t[i].start()

        for i in range(N):
            t[i].join()

        sys.exit(1 if error.is_set() else 0)

    elif args.single:
        if not FOUND_METHOD:
            log("\nerror: cannot find method \"%s\"" % args.single)
            EXIT_STATUS = 1
        sys.exit(EXIT_STATUS)
    else:
        sys.exit(EXIT_STATUS)
