/*
 * C Extension module to test Python interpreter C APIs.
 *
 * The 'test_*' functions exported by this module are run as part of the
 * standard Python regression test, via Lib/test/test_capi.py.
 */

#include "Python.h"

#ifdef WITH_THREAD
#include "pythread.h"
#endif /* WITH_THREAD */
static PyObject *TestError;	/* set to exception object in init */

/* Raise TestError with test_name + ": " + msg, and return NULL. */

static PyObject *
raiseTestError(const char* test_name, const char* msg)
{
	char buf[2048];

	if (strlen(test_name) + strlen(msg) > sizeof(buf) - 50)
		PyErr_SetString(TestError, "internal error msg too large");
	else {
		PyOS_snprintf(buf, sizeof(buf), "%s: %s", test_name, msg);
		PyErr_SetString(TestError, buf);
	}
	return NULL;
}

/* Test #defines from pyconfig.h (particularly the SIZEOF_* defines).

   The ones derived from autoconf on the UNIX-like OSes can be relied
   upon (in the absence of sloppy cross-compiling), but the Windows
   platforms have these hardcoded.  Better safe than sorry.
*/
static PyObject*
sizeof_error(const char* fatname, const char* typename,
        int expected, int got)
{
	char buf[1024];
	PyOS_snprintf(buf, sizeof(buf),
		"%.200s #define == %d but sizeof(%.200s) == %d",
		fatname, expected, typename, got);
	PyErr_SetString(TestError, buf);
	return (PyObject*)NULL;
}

static PyObject*
test_config(PyObject *self)
{
#define CHECK_SIZEOF(FATNAME, TYPE) \
	    if (FATNAME != sizeof(TYPE)) \
    	    	return sizeof_error(#FATNAME, #TYPE, FATNAME, sizeof(TYPE))

	CHECK_SIZEOF(SIZEOF_SHORT, short);
	CHECK_SIZEOF(SIZEOF_INT, int);
	CHECK_SIZEOF(SIZEOF_LONG, long);
	CHECK_SIZEOF(SIZEOF_VOID_P, void*);
	CHECK_SIZEOF(SIZEOF_TIME_T, time_t);
#ifdef HAVE_LONG_LONG
	CHECK_SIZEOF(SIZEOF_LONG_LONG, PY_LONG_LONG);
#endif

#undef CHECK_SIZEOF

	Py_INCREF(Py_None);
	return Py_None;
}

static PyObject*
test_list_api(PyObject *self)
{
	PyObject* list;
	int i;

	/* SF bug 132008:  PyList_Reverse segfaults */
#define NLIST 30
	list = PyList_New(NLIST);
	if (list == (PyObject*)NULL)
		return (PyObject*)NULL;
	/* list = range(NLIST) */
	for (i = 0; i < NLIST; ++i) {
		PyObject* anint = PyInt_FromLong(i);
		if (anint == (PyObject*)NULL) {
			Py_DECREF(list);
			return (PyObject*)NULL;
		}
		PyList_SET_ITEM(list, i, anint);
	}
	/* list.reverse(), via PyList_Reverse() */
	i = PyList_Reverse(list);   /* should not blow up! */
	if (i != 0) {
		Py_DECREF(list);
		return (PyObject*)NULL;
	}
	/* Check that list == range(29, -1, -1) now */
	for (i = 0; i < NLIST; ++i) {
		PyObject* anint = PyList_GET_ITEM(list, i);
		if (PyInt_AS_LONG(anint) != NLIST-1-i) {
			PyErr_SetString(TestError,
			                "test_list_api: reverse screwed up");
			Py_DECREF(list);
			return (PyObject*)NULL;
		}
	}
	Py_DECREF(list);
#undef NLIST

	Py_INCREF(Py_None);
	return Py_None;
}

static int
test_dict_inner(int count)
{
	Py_ssize_t pos = 0, iterations = 0;
	int i;
	PyObject *dict = PyDict_New();
	PyObject *v, *k;

	if (dict == NULL)
		return -1;

	for (i = 0; i < count; i++) {
		v = PyInt_FromLong(i);
		PyDict_SetItem(dict, v, v);
		Py_DECREF(v);
	}

	while (PyDict_Next(dict, &pos, &k, &v)) {
		PyObject *o;
		iterations++;

		i = PyInt_AS_LONG(v) + 1;
		o = PyInt_FromLong(i);
		if (o == NULL)
			return -1;
		if (PyDict_SetItem(dict, k, o) < 0) {
			Py_DECREF(o);
			return -1;
		}
		Py_DECREF(o);
	}

	Py_DECREF(dict);

	if (iterations != count) {
		PyErr_SetString(
			TestError,
			"test_dict_iteration: dict iteration went wrong ");
		return -1;
	} else {
		return 0;
	}
}

static PyObject*
test_dict_iteration(PyObject* self)
{
	int i;

	for (i = 0; i < 200; i++) {
		if (test_dict_inner(i) < 0) {
			return NULL;
		}
	}

	Py_INCREF(Py_None);
	return Py_None;
}


/* Tests of PyLong_{As, From}{Unsigned,}Long(), and (#ifdef HAVE_LONG_LONG)
   PyLong_{As, From}{Unsigned,}LongLong().

   Note that the meat of the test is contained in testcapi_long.h.
   This is revolting, but delicate code duplication is worse:  "almost
   exactly the same" code is needed to test PY_LONG_LONG, but the ubiquitous
   dependence on type names makes it impossible to use a parameterized
   function.  A giant macro would be even worse than this.  A C++ template
   would be perfect.

   The "report an error" functions are deliberately not part of the #include
   file:  if the test fails, you can set a breakpoint in the appropriate
   error function directly, and crawl back from there in the debugger.
*/

#define UNBIND(X)  Py_DECREF(X); (X) = NULL

static PyObject *
raise_test_long_error(const char* msg)
{
	return raiseTestError("test_long_api", msg);
}

#define TESTNAME	test_long_api_inner
#define TYPENAME	long
#define F_S_TO_PY	PyLong_FromLong
#define F_PY_TO_S	PyLong_AsLong
#define F_U_TO_PY	PyLong_FromUnsignedLong
#define F_PY_TO_U	PyLong_AsUnsignedLong

#include "testcapi_long.h"

static PyObject *
test_long_api(PyObject* self)
{
	return TESTNAME(raise_test_long_error);
}

#undef TESTNAME
#undef TYPENAME
#undef F_S_TO_PY
#undef F_PY_TO_S
#undef F_U_TO_PY
#undef F_PY_TO_U

#ifdef HAVE_LONG_LONG

static PyObject *
raise_test_longlong_error(const char* msg)
{
	return raiseTestError("test_longlong_api", msg);
}

#define TESTNAME	test_longlong_api_inner
#define TYPENAME	PY_LONG_LONG
#define F_S_TO_PY	PyLong_FromLongLong
#define F_PY_TO_S	PyLong_AsLongLong
#define F_U_TO_PY	PyLong_FromUnsignedLongLong
#define F_PY_TO_U	PyLong_AsUnsignedLongLong

#include "testcapi_long.h"

static PyObject *
test_longlong_api(PyObject* self, PyObject *args)
{
	return TESTNAME(raise_test_longlong_error);
}

#undef TESTNAME
#undef TYPENAME
#undef F_S_TO_PY
#undef F_PY_TO_S
#undef F_U_TO_PY
#undef F_PY_TO_U

/* Test the L code for PyArg_ParseTuple.  This should deliver a PY_LONG_LONG
   for both long and int arguments.  The test may leak a little memory if
   it fails.
*/
static PyObject *
test_L_code(PyObject *self)
{
	PyObject *tuple, *num;
	PY_LONG_LONG value;

        tuple = PyTuple_New(1);
        if (tuple == NULL)
        	return NULL;

        num = PyLong_FromLong(42);
        if (num == NULL)
        	return NULL;

        PyTuple_SET_ITEM(tuple, 0, num);

        value = -1;
        if (PyArg_ParseTuple(tuple, "L:test_L_code", &value) < 0)
        	return NULL;
        if (value != 42)
        	return raiseTestError("test_L_code",
			"L code returned wrong value for long 42");

	Py_DECREF(num);
        num = PyInt_FromLong(42);
        if (num == NULL)
        	return NULL;

        PyTuple_SET_ITEM(tuple, 0, num);

	value = -1;
        if (PyArg_ParseTuple(tuple, "L:test_L_code", &value) < 0)
        	return NULL;
        if (value != 42)
        	return raiseTestError("test_L_code",
			"L code returned wrong value for int 42");

	Py_DECREF(tuple);
	Py_INCREF(Py_None);
	return Py_None;
}

#endif	/* ifdef HAVE_LONG_LONG */

/* Functions to call PyArg_ParseTuple with integer format codes,
   and return the result.
*/
static PyObject *
getargs_b(PyObject *self, PyObject *args)
{
	unsigned char value;
	if (!PyArg_ParseTuple(args, "b", &value))
		return NULL;
	return PyLong_FromUnsignedLong((unsigned long)value);
}

static PyObject *
getargs_B(PyObject *self, PyObject *args)
{
	unsigned char value;
	if (!PyArg_ParseTuple(args, "B", &value))
		return NULL;
	return PyLong_FromUnsignedLong((unsigned long)value);
}

static PyObject *
getargs_H(PyObject *self, PyObject *args)
{
	unsigned short value;
	if (!PyArg_ParseTuple(args, "H", &value))
		return NULL;
	return PyLong_FromUnsignedLong((unsigned long)value);
}

static PyObject *
getargs_I(PyObject *self, PyObject *args)
{
	unsigned int value;
	if (!PyArg_ParseTuple(args, "I", &value))
		return NULL;
	return PyLong_FromUnsignedLong((unsigned long)value);
}

static PyObject *
getargs_k(PyObject *self, PyObject *args)
{
	unsigned long value;
	if (!PyArg_ParseTuple(args, "k", &value))
		return NULL;
	return PyLong_FromUnsignedLong(value);
}

static PyObject *
getargs_i(PyObject *self, PyObject *args)
{
	int value;
	if (!PyArg_ParseTuple(args, "i", &value))
		return NULL;
	return PyLong_FromLong((long)value);
}

static PyObject *
getargs_l(PyObject *self, PyObject *args)
{
	long value;
	if (!PyArg_ParseTuple(args, "l", &value))
		return NULL;
	return PyLong_FromLong(value);
}

static PyObject *
getargs_n(PyObject *self, PyObject *args)
{
	Py_ssize_t value;
	if (!PyArg_ParseTuple(args, "n", &value))
	return NULL;
	return PyInt_FromSsize_t(value);
}

#ifdef HAVE_LONG_LONG
static PyObject *
getargs_L(PyObject *self, PyObject *args)
{
	PY_LONG_LONG value;
	if (!PyArg_ParseTuple(args, "L", &value))
		return NULL;
	return PyLong_FromLongLong(value);
}

static PyObject *
getargs_K(PyObject *self, PyObject *args)
{
	unsigned PY_LONG_LONG value;
	if (!PyArg_ParseTuple(args, "K", &value))
		return NULL;
	return PyLong_FromUnsignedLongLong(value);
}
#endif

/* This function not only tests the 'k' getargs code, but also the
   PyInt_AsUnsignedLongMask() and PyInt_AsUnsignedLongMask() functions. */
static PyObject *
test_k_code(PyObject *self)
{
	PyObject *tuple, *num;
	unsigned long value;

        tuple = PyTuple_New(1);
        if (tuple == NULL)
        	return NULL;

	/* a number larger than ULONG_MAX even on 64-bit platforms */
        num = PyLong_FromString("FFFFFFFFFFFFFFFFFFFFFFFF", NULL, 16);
        if (num == NULL)
        	return NULL;

	value = PyInt_AsUnsignedLongMask(num);
	if (value != ULONG_MAX)
        	return raiseTestError("test_k_code",
	    "PyInt_AsUnsignedLongMask() returned wrong value for long 0xFFF...FFF");

        PyTuple_SET_ITEM(tuple, 0, num);

        value = 0;
        if (PyArg_ParseTuple(tuple, "k:test_k_code", &value) < 0)
        	return NULL;
        if (value != ULONG_MAX)
        	return raiseTestError("test_k_code",
			"k code returned wrong value for long 0xFFF...FFF");

	Py_DECREF(num);
        num = PyLong_FromString("-FFFFFFFF000000000000000042", NULL, 16);
        if (num == NULL)
        	return NULL;

	value = PyInt_AsUnsignedLongMask(num);
	if (value != (unsigned long)-0x42)
        	return raiseTestError("test_k_code",
	    "PyInt_AsUnsignedLongMask() returned wrong value for long 0xFFF...FFF");

        PyTuple_SET_ITEM(tuple, 0, num);

	value = 0;
        if (PyArg_ParseTuple(tuple, "k:test_k_code", &value) < 0)
        	return NULL;
        if (value != (unsigned long)-0x42)
        	return raiseTestError("test_k_code",
			"k code returned wrong value for long -0xFFF..000042");

	Py_DECREF(tuple);
	Py_INCREF(Py_None);
	return Py_None;
}

#ifdef Py_USING_UNICODE

/* Test the u and u# codes for PyArg_ParseTuple. May leak memory in case
   of an error.
*/
static PyObject *
test_u_code(PyObject *self)
{
	PyObject *tuple, *obj;
	Py_UNICODE *value;
	int len;

        tuple = PyTuple_New(1);
        if (tuple == NULL)
        	return NULL;

        obj = PyUnicode_Decode("test", strlen("test"),
			       "ascii", NULL);
        if (obj == NULL)
        	return NULL;

        PyTuple_SET_ITEM(tuple, 0, obj);

        value = 0;
        if (PyArg_ParseTuple(tuple, "u:test_u_code", &value) < 0)
        	return NULL;
        if (value != PyUnicode_AS_UNICODE(obj))
        	return raiseTestError("test_u_code",
			"u code returned wrong value for u'test'");
        value = 0;
        if (PyArg_ParseTuple(tuple, "u#:test_u_code", &value, &len) < 0)
        	return NULL;
        if (value != PyUnicode_AS_UNICODE(obj) ||
	    len != PyUnicode_GET_SIZE(obj))
        	return raiseTestError("test_u_code",
			"u# code returned wrong values for u'test'");

	Py_DECREF(tuple);
	Py_INCREF(Py_None);
	return Py_None;
}

static PyObject *
codec_incrementalencoder(PyObject *self, PyObject *args)
{
	const char *encoding, *errors = NULL;
	if (!PyArg_ParseTuple(args, "s|s:test_incrementalencoder",
			      &encoding, &errors))
		return NULL;
	return PyCodec_IncrementalEncoder(encoding, errors);
}

static PyObject *
codec_incrementaldecoder(PyObject *self, PyObject *args)
{
	const char *encoding, *errors = NULL;
	if (!PyArg_ParseTuple(args, "s|s:test_incrementaldecoder",
			      &encoding, &errors))
		return NULL;
	return PyCodec_IncrementalDecoder(encoding, errors);
}

#endif

/* Simple test of _PyLong_NumBits and _PyLong_Sign. */
static PyObject *
test_long_numbits(PyObject *self)
{
	struct triple {
		long input;
		size_t nbits;
		int sign;
	} testcases[] = {{0, 0, 0},
			 {1L, 1, 1},
			 {-1L, 1, -1},
			 {2L, 2, 1},
			 {-2L, 2, -1},
			 {3L, 2, 1},
			 {-3L, 2, -1},
			 {4L, 3, 1},
			 {-4L, 3, -1},
			 {0x7fffL, 15, 1},	/* one Python long digit */
			 {-0x7fffL, 15, -1},
			 {0xffffL, 16, 1},
			 {-0xffffL, 16, -1},
			 {0xfffffffL, 28, 1},
			 {-0xfffffffL, 28, -1}};
	int i;

	for (i = 0; i < sizeof(testcases) / sizeof(struct triple); ++i) {
		PyObject *plong = PyLong_FromLong(testcases[i].input);
		size_t nbits = _PyLong_NumBits(plong);
		int sign = _PyLong_Sign(plong);

		Py_DECREF(plong);
		if (nbits != testcases[i].nbits)
			return raiseTestError("test_long_numbits",
					"wrong result for _PyLong_NumBits");
		if (sign != testcases[i].sign)
			return raiseTestError("test_long_numbits",
					"wrong result for _PyLong_Sign");
	}
	Py_INCREF(Py_None);
	return Py_None;
}

/* Example passing NULLs to PyObject_Str(NULL) and PyObject_Unicode(NULL). */

static PyObject *
test_null_strings(PyObject *self)
{
	PyObject *o1 = PyObject_Str(NULL), *o2 = PyObject_Unicode(NULL);
	PyObject *tuple = PyTuple_Pack(2, o1, o2);
	Py_XDECREF(o1);
	Py_XDECREF(o2);
	return tuple;
}

static PyObject *
raise_exception(PyObject *self, PyObject *args)
{
	PyObject *exc;
	PyObject *exc_args, *v;
	int num_args, i;

	if (!PyArg_ParseTuple(args, "Oi:raise_exception",
			      &exc, &num_args))
		return NULL;

	exc_args = PyTuple_New(num_args);
	if (exc_args == NULL)
		return NULL;
	for (i = 0; i < num_args; ++i) {
		v = PyInt_FromLong(i);
		if (v == NULL) {
			Py_DECREF(exc_args);
			return NULL;
		}
		PyTuple_SET_ITEM(exc_args, i, v);
	}
	PyErr_SetObject(exc, exc_args);
	Py_DECREF(exc_args);
	return NULL;
}

#ifdef WITH_THREAD

/* test_thread_state spawns a thread of its own, and that thread releases
 * `thread_done` when it's finished.  The driver code has to know when the
 * thread finishes, because the thread uses a PyObject (the callable) that
 * may go away when the driver finishes.  The former lack of this explicit
 * synchronization caused rare segfaults, so rare that they were seen only
 * on a Mac buildbot (although they were possible on any box).
 */
static PyThread_type_lock thread_done = NULL;

static void
_make_call(void *callable)
{
	PyObject *rc;
	PyGILState_STATE s = PyGILState_Ensure();
	rc = PyObject_CallFunction(callable, "");
	Py_XDECREF(rc);
	PyGILState_Release(s);
}

/* Same thing, but releases `thread_done` when it returns.  This variant
 * should be called only from threads spawned by test_thread_state().
 */
static void
_make_call_from_thread(void *callable)
{
	_make_call(callable);
	PyThread_release_lock(thread_done);
}

static PyObject *
test_thread_state(PyObject *self, PyObject *args)
{
	PyObject *fn;

	if (!PyArg_ParseTuple(args, "O:test_thread_state", &fn))
		return NULL;

	/* Ensure Python is set up for threading */
	PyEval_InitThreads();
	thread_done = PyThread_allocate_lock();
	if (thread_done == NULL)
		return PyErr_NoMemory();
	PyThread_acquire_lock(thread_done, 1);

	/* Start a new thread with our callback. */
	PyThread_start_new_thread(_make_call_from_thread, fn);
	/* Make the callback with the thread lock held by this thread */
	_make_call(fn);
	/* Do it all again, but this time with the thread-lock released */
	Py_BEGIN_ALLOW_THREADS
	_make_call(fn);
	PyThread_acquire_lock(thread_done, 1);  /* wait for thread to finish */
	Py_END_ALLOW_THREADS

	/* And once more with and without a thread
	   XXX - should use a lock and work out exactly what we are trying
	   to test <wink>
	*/
	Py_BEGIN_ALLOW_THREADS
	PyThread_start_new_thread(_make_call_from_thread, fn);
	_make_call(fn);
	PyThread_acquire_lock(thread_done, 1);  /* wait for thread to finish */
	Py_END_ALLOW_THREADS

	PyThread_free_lock(thread_done);
	Py_RETURN_NONE;
}
#endif

/* Some tests of PyString_FromFormat().  This needs more tests. */
static PyObject *
test_string_from_format(PyObject *self, PyObject *args)
{
	PyObject *result;
	char *msg;

#define CHECK_1_FORMAT(FORMAT, TYPE) 			\
	result = PyString_FromFormat(FORMAT, (TYPE)1);	\
	if (result == NULL)				\
		return NULL;				\
	if (strcmp(PyString_AsString(result), "1")) {	\
		msg = FORMAT " failed at 1";		\
		goto Fail;				\
	}						\
	Py_DECREF(result)

	CHECK_1_FORMAT("%d", int);
	CHECK_1_FORMAT("%ld", long);
	/* The z width modifier was added in Python 2.5. */
	CHECK_1_FORMAT("%zd", Py_ssize_t);

	/* The u type code was added in Python 2.5. */
	CHECK_1_FORMAT("%u", unsigned int);
	CHECK_1_FORMAT("%lu", unsigned long);
	CHECK_1_FORMAT("%zu", size_t);

	Py_RETURN_NONE;

 Fail:
 	Py_XDECREF(result);
	return raiseTestError("test_string_from_format", msg);

#undef CHECK_1_FORMAT
}

static PyMethodDef TestMethods[] = {
	{"raise_exception",	raise_exception,		 METH_VARARGS},
	{"test_config",		(PyCFunction)test_config,	 METH_NOARGS},
	{"test_list_api",	(PyCFunction)test_list_api,	 METH_NOARGS},
	{"test_dict_iteration",	(PyCFunction)test_dict_iteration,METH_NOARGS},
	{"test_long_api",	(PyCFunction)test_long_api,	 METH_NOARGS},
	{"test_long_numbits",	(PyCFunction)test_long_numbits,	 METH_NOARGS},
	{"test_k_code",		(PyCFunction)test_k_code,	 METH_NOARGS},
	{"test_null_strings",	(PyCFunction)test_null_strings,	 METH_NOARGS},
	{"test_string_from_format", (PyCFunction)test_string_from_format, METH_NOARGS},

	{"getargs_b",		getargs_b,			 METH_VARARGS},
	{"getargs_B",		getargs_B,			 METH_VARARGS},
	{"getargs_H",		getargs_H,			 METH_VARARGS},
	{"getargs_I",		getargs_I,			 METH_VARARGS},
	{"getargs_k",		getargs_k,			 METH_VARARGS},
	{"getargs_i",		getargs_i,			 METH_VARARGS},
	{"getargs_l",		getargs_l,			 METH_VARARGS},
	{"getargs_n",		getargs_n, 			 METH_VARARGS},
#ifdef HAVE_LONG_LONG
	{"getargs_L",		getargs_L,			 METH_VARARGS},
	{"getargs_K",		getargs_K,			 METH_VARARGS},
	{"test_longlong_api",	test_longlong_api,		 METH_NOARGS},
	{"test_L_code",		(PyCFunction)test_L_code,	 METH_NOARGS},
	{"codec_incrementalencoder",
	 (PyCFunction)codec_incrementalencoder,	 METH_VARARGS},
	{"codec_incrementaldecoder",
	 (PyCFunction)codec_incrementaldecoder,	 METH_VARARGS},
#endif
#ifdef Py_USING_UNICODE
	{"test_u_code",		(PyCFunction)test_u_code,	 METH_NOARGS},
#endif
#ifdef WITH_THREAD
	{"_test_thread_state",  test_thread_state, 		 METH_VARARGS},
#endif
	{NULL, NULL} /* sentinel */
};

#define AddSym(d, n, f, v) {PyObject *o = f(v); PyDict_SetItemString(d, n, o); Py_DECREF(o);}

PyMODINIT_FUNC
init_testcapi(void)
{
	PyObject *m;

	m = Py_InitModule("_testcapi", TestMethods);
	if (m == NULL)
		return;

	PyModule_AddObject(m, "UCHAR_MAX", PyInt_FromLong(UCHAR_MAX));
	PyModule_AddObject(m, "USHRT_MAX", PyInt_FromLong(USHRT_MAX));
	PyModule_AddObject(m, "UINT_MAX",  PyLong_FromUnsignedLong(UINT_MAX));
	PyModule_AddObject(m, "ULONG_MAX", PyLong_FromUnsignedLong(ULONG_MAX));
	PyModule_AddObject(m, "INT_MIN", PyInt_FromLong(INT_MIN));
	PyModule_AddObject(m, "LONG_MIN", PyInt_FromLong(LONG_MIN));
	PyModule_AddObject(m, "PY_SSIZE_T_MIN", PyInt_FromSsize_t(PY_SSIZE_T_MIN));
	PyModule_AddObject(m, "INT_MAX", PyInt_FromLong(INT_MAX));
	PyModule_AddObject(m, "LONG_MAX", PyInt_FromLong(LONG_MAX));
	PyModule_AddObject(m, "PY_SSIZE_T_MAX", PyInt_FromSsize_t(PY_SSIZE_T_MAX));

	TestError = PyErr_NewException("_testcapi.error", NULL, NULL);
	Py_INCREF(TestError);
	PyModule_AddObject(m, "error", TestError);
}
