
/* MPZ module */

/* This module provides an interface to an alternate Multi-Precision
   library, GNU MP in this case */

/* XXX note: everywhere where mpz_size is called,
   sizeof (limb) == sizeof (long)  has been assumed. */
   

/* MPZ objects */

#include "Python.h"

#include <assert.h>
#include <sys/types.h>		/* For size_t */

/*
**	These are the cpp-flags used in this file...
**
**
** MPZ_MDIV_BUG		works around the mpz_m{div,mod,...} routines.
** 			This bug has been fixed in a later release of
** 			GMP.
** 
** MPZ_GET_STR_BUG	mpz_get_str corrupts memory, seems to be fixed
** 			in a later release
** 
** MPZ_DEBUG		generates a bunch of diagnostic messages
** 
** MPZ_SPARE_MALLOC	if set, results in extra code that tries to
** 			minimize the creation of extra objects.
** 
** MPZ_TEST_DIV		extra diagnostic output on stderr, when division
** 			routines are involved
** 
** MPZ_LIB_DOES_CHECKING	if set, assumes that mpz library doesn't call
** 			alloca with arg < 0 (when casted to a signed
** 			integral type).
** 
** MPZ_CONVERSIONS_AS_METHODS	if set, presents the conversions as
** 			methods. e.g., `mpz(5).long() == 5L'
** 			Later, Guido provided an interface to the
** 			standard functions. So this flag has no been
** 			cleared, and `long(mpz(5)) == 5L'
** 
** MP_TEST_ALLOC	If set, you would discover why MPZ_GET_STR_BUG
**			is needed
** 
** MAKEDUMMYINT		Must be set if dynamic linking will be used
*/


/*
** IMHO, mpz_m{div,mod,divmod}() do the wrong things when the denominator < 0
** This has been fixed with gmp release 2.0
*/
/*#define MPZ_MDIV_BUG fixed the (for me) nexessary parts in libgmp.a */
/*
** IMO, mpz_get_str() assumes a bit too large target space, if he doesn't
** allocate it himself
*/

#include "gmp.h"

#if __GNU_MP__ + 0 == 2
#define GMP2
#define BITS_PER_MP_LIMB mp_bits_per_limb
#else
#define MPZ_GET_STR_BUG
#include "gmp-mparam.h"
#endif

typedef struct {
	PyObject_HEAD
        MP_INT	mpz;		/* the actual number */
} mpzobject;

staticforward PyTypeObject MPZtype;

#define is_mpzobject(v)		((v)->ob_type == &MPZtype)

static const char initialiser_name[] = "mpz";

/* #define MPZ_DEBUG */

static mpzobject *
newmpzobject(void)
{
	mpzobject *mpzp;


#ifdef MPZ_DEBUG
	fputs( "mpz_object() called...\n", stderr );
#endif /* def MPZ_DEBUG */
	mpzp = PyObject_New(mpzobject, &MPZtype);
	if (mpzp == NULL)
		return NULL;

	mpz_init(&mpzp->mpz);	/* actual initialisation */
	return mpzp;
} /* newmpzobject() */

#ifdef MPZ_GET_STR_BUG
#include "longlong.h"
#endif /* def MPZ_GET_STR_BUG */

static PyObject *
mpz_format(PyObject *objp, int base, unsigned char withname)
{
	mpzobject *mpzp = (mpzobject *)objp;
	PyStringObject *strobjp;
	size_t i;
	int cmpres;
	int taglong;
	char *cp;
	char prefix[5], *tcp;


	tcp = &prefix[0];

	if (mpzp == NULL || !is_mpzobject(mpzp)) {
		PyErr_BadInternalCall();
		return NULL;
	}

	assert(base >= 2 && base <= 36);

	if (withname)
		i = strlen(initialiser_name) + 2; /* e.g. 'mpz(' + ')' */
	else
		i = 0;

	if ((cmpres = mpz_cmp_si(&mpzp->mpz, 0L)) == 0)
		base = 10;	/* '0' in every base, right */
	else if (cmpres < 0) {
		*tcp++ = '-';
		i += 1;		/* space to hold '-' */
	}

#ifdef MPZ_DEBUG
	fprintf(stderr, "mpz_format: mpz_sizeinbase %d\n",
		(int)mpz_sizeinbase(&mpzp->mpz, base));
#endif /* def MPZ_DEBUG */
#ifdef MPZ_GET_STR_BUG
#ifdef GMP2
	i += ((size_t) abs(mpzp->mpz._mp_size) * BITS_PER_MP_LIMB
	      * __mp_bases[base].chars_per_bit_exactly) + 1;
#else
	i += ((size_t) abs(mpzp->mpz.size) * BITS_PER_MP_LIMB
	      * __mp_bases[base].chars_per_bit_exactly) + 1;
#endif
#else /* def MPZ_GET_STR_BUG */
	i += (int)mpz_sizeinbase(&mpzp->mpz, base);
#endif /* def MPZ_GET_STR_BUG else */

	if (base == 16) {
		*tcp++ = '0';
		*tcp++ = 'x';
		i += 2;		/* space to hold '0x' */
	}
	else if (base == 8) {
		*tcp++ = '0';
		i += 1;		/* space to hold the extra '0' */
	}
	else if (base > 10) {
		*tcp++ = '0' + base / 10;
		*tcp++ = '0' + base % 10;
		*tcp++ = '#';
		i += 3;		/* space to hold e.g. '12#' */
	}
	else if (base < 10) {
		*tcp++ = '0' + base;
		*tcp++ = '#';
		i += 2;		/* space to hold e.g. '6#' */
	}

	/*
	** the following code looks if we need a 'L' attached to the number
	** it will also attach an 'L' to the value -0x80000000
	*/
	taglong = 0;
	if (mpz_size(&mpzp->mpz) > 1
	    || (long)mpz_get_ui(&mpzp->mpz) < 0L) {
		taglong = 1;
		i += 1;		/* space to hold 'L' */
	}

#ifdef MPZ_DEBUG
	fprintf(stderr, "mpz_format: requesting string size %d\n", i);
#endif /* def MPZ_DEBUG */	
	if ((strobjp =
	     (PyStringObject *)PyString_FromStringAndSize((char *)0, i))
	    == NULL)
		return NULL;

	/* get the beginning of the string memory and start copying things */
	cp = PyString_AS_STRING(strobjp);
	if (withname) {
		strcpy(cp, initialiser_name);
		cp += strlen(initialiser_name);
		*cp++ = '('; /*')'*/
	}

	/* copy the already prepared prefix; e.g. sign and base indicator */
	*tcp = '\0';
	strcpy(cp, prefix);
	cp += tcp - prefix;

	/* since' we have the sign already, let the lib think it's a positive
	   number */
	if (cmpres < 0)
		mpz_neg(&mpzp->mpz,&mpzp->mpz);	/* hack Hack HAck HACk HACK */
	(void)mpz_get_str(cp, base, &mpzp->mpz);
	if (cmpres < 0)
		mpz_neg(&mpzp->mpz,&mpzp->mpz);	/* hack Hack HAck HACk HACK */
#ifdef MPZ_DEBUG
	fprintf(stderr, "mpz_format: base (ultim) %d, mpz_get_str: %s\n",
		base, cp);
#endif /* def MPZ_DEBUG */
	cp += strlen(cp);

	if (taglong)
		*cp++ = 'L';
	if (withname)
		*cp++ = /*'('*/ ')';

	*cp = '\0';

#ifdef MPZ_DEBUG
	fprintf(stderr,
		"mpz_format: cp (str end) %p, begin %p, diff %d, i %d\n",
		cp, PyString_AS_STRING(strobjp),
		cp - PyString_AS_STRING(strobjp), i);
#endif /* def MPZ_DEBUG */	
	assert(cp - PyString_AS_STRING(strobjp) <= i);

	if (cp - PyString_AS_STRING(strobjp) != i) {
		strobjp->ob_size -= i - (cp - PyString_AS_STRING(strobjp));
	}

	return (PyObject *)strobjp;
} /* mpz_format() */

/* MPZ methods */

static void
mpz_dealloc(mpzobject *mpzp)
{
#ifdef MPZ_DEBUG
	fputs( "mpz_dealloc() called...\n", stderr );
#endif /* def MPZ_DEBUG */
	mpz_clear(&mpzp->mpz);
	PyObject_Del(mpzp);
} /* mpz_dealloc() */


/* pointers to frequently used values 0, 1 and -1 */
static mpzobject *mpz_value_zero, *mpz_value_one, *mpz_value_mone;

static int
mpz_compare(mpzobject *a, mpzobject *b)
{
	int cmpres;


	/* guido sez it's better to return -1, 0 or 1 */
	return (cmpres = mpz_cmp( &a->mpz, &b->mpz )) == 0 ? 0
		: cmpres > 0 ? 1 : -1;
} /* mpz_compare() */

static PyObject *
mpz_addition(mpzobject *a, mpzobject *b)
{
	mpzobject *z;

	
#ifdef MPZ_SPARE_MALLOC
	if (mpz_cmp_ui(&a->mpz, (unsigned long int)0) == 0) {
		Py_INCREF(b);
		return (PyObject *)b;
	}

	if (mpz_cmp_ui(&b->mpz, (unsigned long int)0) == 0) {
		Py_INCREF(a);
		return (PyObject *)a;
	}
#endif /* def MPZ_SPARE_MALLOC */

	if ((z = newmpzobject()) == NULL)
		return NULL;
	
	mpz_add(&z->mpz, &a->mpz, &b->mpz);
	return (PyObject *)z;
} /* mpz_addition() */

static PyObject *
mpz_substract(mpzobject *a, mpzobject *b)
{
	mpzobject *z;

	
#ifdef MPZ_SPARE_MALLOC
	if (mpz_cmp_ui(&b->mpz, (unsigned long int)0) == 0) {
		Py_INCREF(a);
		return (PyObject *)a;
	}
#endif /* MPZ_SPARE_MALLOC */	

	if ((z = newmpzobject()) == NULL)
		return NULL;

	mpz_sub(&z->mpz, &a->mpz, &b->mpz);
	return (PyObject *)z;
} /* mpz_substract() */

static PyObject *
mpz_multiply(mpzobject *a, mpzobject *b)
{
#ifdef MPZ_SPARE_MALLOC
	int cmpres;
#endif /* def MPZ_SPARE_MALLOC */
	mpzobject *z;


#ifdef MPZ_SPARE_MALLOC
	if ((cmpres = mpz_cmp_ui(&a->mpz, (unsigned long int)0)) == 0) {
		Py_INCREF(mpz_value_zero);
		return (PyObject *)mpz_value_zero;
	}
	if (cmpres > 0 && mpz_cmp_ui(&a->mpz, (unsigned long int)1) == 0) {
		Py_INCREF(b);
		return (PyObject *)b;
	}

	if ((cmpres = mpz_cmp_ui(&b->mpz, (unsigned long_int)0)) == 0) {
		Py_INCREF(mpz_value_zero);
		return (PyObject *)mpz_value_zero;
	}
	if (cmpres > 0 && mpz_cmp_ui(&b->mpz, (unsigned long int)1) == 0) {
		Py_INCREF(a);
		return (PyObject *)a;
	}
#endif /* MPZ_SPARE_MALLOC */

	if ((z = newmpzobject()) == NULL)
		return NULL;

	mpz_mul( &z->mpz, &a->mpz, &b->mpz );
	return (PyObject *)z;
	
} /* mpz_multiply() */

static PyObject *
mpz_divide(mpzobject *a, mpzobject *b)
{
#ifdef MPZ_SPARE_MALLOC
	int cmpres;
#endif /* def MPZ_SPARE_MALLOC */
	mpzobject *z;


	if ((
#ifdef MPZ_SPARE_MALLOC
	     cmpres =
#endif /* def MPZ_SPARE_MALLOC */
	     mpz_cmp_ui(&b->mpz, (unsigned long int)0)) == 0) {
		PyErr_SetString(PyExc_ZeroDivisionError, "mpz./ by zero");
		return NULL;
	}
#ifdef MPZ_SPARE_MALLOC
	if (cmpres > 0 && mpz_cmp_ui(&b->mpz(unsigned long int)1) == 0) {
		Py_INCREF(a);
		return (PyObject *)a;
	}
#endif /* def MPZ_SPARE_MALLOC */

	if ((z = newmpzobject()) == NULL)
		return NULL;

#ifdef MPZ_TEST_DIV
	fputs("mpz_divide:  div result", stderr);
	mpz_div(&z->mpz, &a->mpz, &b->mpz);
	mpz_out_str(stderr, 10, &z->mpz);
	putc('\n', stderr);
#endif /* def MPZ_TEST_DIV */
#ifdef MPZ_MDIV_BUG
	if ((mpz_cmp_ui(&a->mpz, (unsigned long int)0) < 0)
	    != (mpz_cmp_ui(&b->mpz, (unsigned long int)0) < 0)) {
		/*
		** numerator has other sign than denominator: we have
		** to look at the remainder for a correction, since mpz_mdiv
		** also calls mpz_divmod, I can as well do it myself
		*/
		MP_INT tmpmpz;


		mpz_init(&tmpmpz);
		mpz_divmod(&z->mpz, &tmpmpz, &a->mpz, &b->mpz);

		if (mpz_cmp_ui(&tmpmpz, (unsigned long int)0) != 0)
			mpz_sub_ui(&z->mpz, &z->mpz, (unsigned long int)1);

		mpz_clear(&tmpmpz);
	}
	else
		mpz_div(&z->mpz, &a->mpz, &b->mpz);
		/* the ``naive'' implementation does it right for operands
		   having the same sign */

#else /* def MPZ_MDIV_BUG */
	mpz_mdiv(&z->mpz, &a->mpz, &b->mpz);
#endif /* def MPZ_MDIV_BUG else */
#ifdef MPZ_TEST_DIV
	fputs("mpz_divide: mdiv result", stderr);
	mpz_out_str(stderr, 10, &z->mpz);
	putc('\n', stderr);
#endif /* def MPZ_TEST_DIV */
	return (PyObject *)z;
	
} /* mpz_divide() */

static PyObject *
mpz_remainder(mpzobject *a, mpzobject *b)
{
#ifdef MPZ_SPARE_MALLOC
	int cmpres;
#endif /* def MPZ_SPARE_MALLOC */	
	mpzobject *z;

	
	if ((
#ifdef MPZ_SPARE_MALLOC	     
	     cmpres =
#endif /* def MPZ_SPARE_MALLOC */	
	     mpz_cmp_ui(&b->mpz, (unsigned long int)0)) == 0) {
		PyErr_SetString(PyExc_ZeroDivisionError, "mpz.% by zero");
		return NULL;
	}
#ifdef MPZ_SPARE_MALLOC
	if (cmpres > 0) {
		if ((cmpres = mpz_cmp_ui(&b->mpz, (unsigned long int)2)) == 0)
		{
			Py_INCREF(mpz_value_one);
			return (PyObject *)mpz_value_one;
		}
		if (cmpres < 0) {
			/* b must be 1 now */
			Py_INCREF(mpz_value_zero);
			return (PyObject *)mpz_value_zero;
		}
	}
#endif /* def MPZ_SPARE_MALLOC */	

	if ((z = newmpzobject()) == NULL)
		return NULL;

#ifdef MPZ_TEST_DIV
	fputs("mpz_remain:  mod result", stderr);
	mpz_mod(&z->mpz, &a->mpz, &b->mpz);
	mpz_out_str(stderr, 10, &z->mpz);
	putc('\n', stderr);
#endif /* def MPZ_TEST_DIV */
#ifdef MPZ_MDIV_BUG

	/* the ``naive'' implementation does it right for operands
	   having the same sign */
	mpz_mod(&z->mpz, &a->mpz, &b->mpz);

	/* assumption: z, a and b all point to different locations */
	if ((mpz_cmp_ui(&a->mpz, (unsigned long int)0) < 0)
	    != (mpz_cmp_ui(&b->mpz, (unsigned long int)0) < 0)
	    && mpz_cmp_ui(&z->mpz, (unsigned long int)0) != 0)
		mpz_add(&z->mpz, &z->mpz, &b->mpz);
		/*
		** numerator has other sign than denominator: we have
		** to look at the remainder for a correction, since mpz_mdiv
		** also calls mpz_divmod, I can as well do it myself
		*/
#else /* def MPZ_MDIV_BUG */
	mpz_mmod(&z->mpz, &a->mpz, &b->mpz);
#endif /* def MPZ_MDIV_BUG else */
#ifdef MPZ_TEST_DIV
	fputs("mpz_remain: mmod result", stderr);
	mpz_out_str(stderr, 10, &z->mpz);
	putc('\n', stderr);
#endif /* def MPZ_TEST_DIV */
	return (PyObject *)z;
	
} /* mpz_remainder() */

static PyObject *
mpz_div_and_mod(mpzobject *a, mpzobject *b)
{
	PyObject *z = NULL;
	mpzobject *x = NULL, *y = NULL;


	if (mpz_cmp_ui(&b->mpz, (unsigned long int)0) == 0) {
		PyErr_SetString(PyExc_ZeroDivisionError, "mpz.divmod by zero");
		return NULL;
	}

	if ((z = PyTuple_New(2)) == NULL
	    || (x = newmpzobject()) == NULL
	    || (y = newmpzobject()) == NULL) {
		Py_XDECREF(z);
		Py_XDECREF(x);
		Py_XDECREF(y);
		return NULL;
	}

#ifdef MPZ_TEST_DIV
	fputs("mpz_divmod:  dm  result", stderr);
	mpz_divmod(&x->mpz, &y->mpz, &a->mpz, &b->mpz);
	mpz_out_str(stderr, 10, &x->mpz);
	putc('\n', stderr);
	mpz_out_str(stderr, 10, &y->mpz);
	putc('\n', stderr);
#endif /* def MPZ_TEST_DIV */
#ifdef MPZ_MDIV_BUG
	mpz_divmod(&x->mpz, &y->mpz, &a->mpz, &b->mpz);
	if ((mpz_cmp_ui(&a->mpz, (unsigned long int)0) < 0)
	    != (mpz_cmp_ui(&b->mpz, (unsigned long int)0) < 0)
	    && mpz_cmp_ui(&y->mpz, (unsigned long int)0) != 0) {
		/*
		** numerator has other sign than denominator: we have
		** to look at the remainder for a correction.
		*/
		mpz_add(&y->mpz, &y->mpz, &b->mpz);
		mpz_sub_ui(&x->mpz, &x->mpz, (unsigned long int)1);
	}
#else /* def MPZ_MDIV_BUG */
	mpz_mdivmod( &x->mpz, &y->mpz, &a->mpz, &b->mpz );
#endif /* def MPZ_MDIV_BUG else */
#ifdef MPZ_TEST_DIV
	fputs("mpz_divmod: mdm  result", stderr);
	mpz_out_str(stderr, 10, &x->mpz);
	putc('\n', stderr);
	mpz_out_str(stderr, 10, &y->mpz);
	putc('\n', stderr);
#endif /* def MPZ_TEST_DIV */

	(void)PyTuple_SetItem(z, 0, (PyObject *)x);
	(void)PyTuple_SetItem(z, 1, (PyObject *)y);
	
	return z;
} /* mpz_div_and_mod() */

static PyObject *
mpz_power(mpzobject *a, mpzobject *b, mpzobject *m)
{
	mpzobject *z;
	int cmpres;

 	if ((PyObject *)m != Py_None) {
		mpzobject *z2;
		Py_INCREF(Py_None);
		z=(mpzobject *)mpz_power(a, b, (mpzobject *)Py_None);
		Py_DECREF(Py_None);
		if (z==NULL) return((PyObject *)z);
		z2=(mpzobject *)mpz_remainder(z, m);
		Py_DECREF(z);
		return((PyObject *)z2);
	}	    

	if ((cmpres = mpz_cmp_ui(&b->mpz, (unsigned long int)0)) == 0) {
		/* the gnu-mp lib sets pow(0,0) to 0, we to 1 */

		Py_INCREF(mpz_value_one);
		return (PyObject *)mpz_value_one;
	}
		
	if (cmpres < 0) {
		PyErr_SetString(PyExc_ValueError,
				"mpz.pow to negative exponent");
		return NULL;
	}

	if ((cmpres = mpz_cmp_ui(&a->mpz, (unsigned long int)0)) == 0) {
		/* the base is 0 */

		Py_INCREF(mpz_value_zero);
		return (PyObject *)mpz_value_zero;
	}
	else if (cmpres > 0
		 && mpz_cmp_ui(&a->mpz, (unsigned long int)1) == 0) {
		/* the base is 1 */

		Py_INCREF(mpz_value_one);
		return (PyObject *)mpz_value_one;
	}
	else if (cmpres < 0
		 && mpz_cmp_si(&a->mpz, (long int)-1) == 0) {

		MP_INT tmpmpz;
		/* the base is -1: pow(-1, any) == 1,-1 for even,uneven b */
		/* XXX this code needs to be optimized: what's better?
		   mpz_mmod_ui or mpz_mod_2exp, I choose for the latter
		   for *un*obvious reasons */

		/* is the exponent even? */
		mpz_init(&tmpmpz);

		/* look to the remainder after a division by (1 << 1) */
		mpz_mod_2exp(&tmpmpz, &b->mpz, (unsigned long int)1);

		if (mpz_cmp_ui(&tmpmpz, (unsigned int)0) == 0) {
			mpz_clear(&tmpmpz);
			Py_INCREF(mpz_value_one);
			return (PyObject *)mpz_value_one;
		}
		mpz_clear(&tmpmpz);
		Py_INCREF(mpz_value_mone);
		return (PyObject *)mpz_value_mone;
	}

#ifdef MPZ_LIB_DOES_CHECKING
	/* check if it's doable: sizeof(exp) > sizeof(long) &&
	   abs(base) > 1 ?? --> No Way */
	if (mpz_size(&b->mpz) > 1)
		return (PyObject *)PyErr_NoMemory();
#else /* def MPZ_LIB_DOES_CHECKING */
	/* wet finger method */
	if (mpz_cmp_ui(&b->mpz, (unsigned long int)0x10000) >= 0) {
		PyErr_SetString(PyExc_ValueError,
				"mpz.pow outrageous exponent");
		return NULL;
	}
#endif /* def MPZ_LIB_DOES_CHECKING else */

	if ((z = newmpzobject()) == NULL)
		return NULL;
	
	mpz_pow_ui(&z->mpz, &a->mpz, mpz_get_ui(&b->mpz));
	
	return (PyObject *)z;
} /* mpz_power() */


static PyObject *
mpz_negative(mpzobject *v)
{
	mpzobject *z;

	
#ifdef MPZ_SPARE_MALLOC
	if (mpz_cmp_ui(&v->mpz, (unsigned long int)0) == 0) {
		/* -0 == 0 */
		Py_INCREF(v);
		return (PyObject *)v;
	}
#endif /* def MPZ_SPARE_MALLOC */

	if ((z = newmpzobject()) == NULL)
		return NULL;

	mpz_neg(&z->mpz, &v->mpz);
	return (PyObject *)z;
} /* mpz_negative() */


static PyObject *
mpz_positive(mpzobject *v)
{
	Py_INCREF(v);
	return (PyObject *)v;
} /* mpz_positive() */


static PyObject *
mpz_absolute(mpzobject *v)
{
	mpzobject *z;

	
	if (mpz_cmp_ui(&v->mpz, (unsigned long int)0) >= 0) {
		Py_INCREF(v);
		return (PyObject *)v;
	}

	if ((z = newmpzobject()) == NULL)
		return NULL;

	mpz_neg(&z->mpz, &v->mpz);
	return (PyObject *)z;
} /* mpz_absolute() */

static int
mpz_nonzero(mpzobject *v)
{
	return mpz_cmp_ui(&v->mpz, (unsigned long int)0) != 0;
} /* mpz_nonzero() */
		
static PyObject *
py_mpz_invert(mpzobject *v)
{
	mpzobject *z;


	/* I think mpz_com does exactly what needed */
	if ((z = newmpzobject()) == NULL)
		return NULL;

	mpz_com(&z->mpz, &v->mpz);
	return (PyObject *)z;
} /* py_mpz_invert() */

static PyObject *
mpz_lshift(mpzobject *a, mpzobject *b)
{
	int cmpres;
	mpzobject *z;


	if ((cmpres = mpz_cmp_ui(&b->mpz, (unsigned long int)0)) == 0) {
		/* a << 0 == a */
		Py_INCREF(a);
		return (PyObject *)a;
	}

	if (cmpres < 0) {
		PyErr_SetString(PyExc_ValueError,
				"mpz.<< negative shift count");
		return NULL;
	}

#ifdef MPZ_LIB_DOES_CHECKING
	if (mpz_size(&b->mpz) > 1)
		return (PyObject *)PyErr_NoMemory();
#else /* def MPZ_LIB_DOES_CHECKING */
	/* wet finger method */
	if (mpz_cmp_ui(&b->mpz, (unsigned long int)0x10000) >= 0) {
		PyErr_SetString(PyExc_ValueError,
				"mpz.<< outrageous shift count");
		return NULL;
	}
#endif /* def MPZ_LIB_DOES_CHECKING else */

	if ((z = newmpzobject()) == NULL)
		return NULL;

	mpz_mul_2exp(&z->mpz, &a->mpz, mpz_get_ui(&b->mpz));
	return (PyObject *)z;
} /* mpz_lshift() */

static PyObject *
mpz_rshift(mpzobject *a, mpzobject *b)
{
	int cmpres;
	mpzobject *z;


	if ((cmpres = mpz_cmp_ui(&b->mpz, (unsigned long int)0)) == 0) {
		/* a >> 0 == a */
		Py_INCREF(a);
		return (PyObject *)a;
	}

	if (cmpres < 0) {
		PyErr_SetString(PyExc_ValueError,
				"mpz.>> negative shift count");
		return NULL;
	}

	if (mpz_size(&b->mpz) > 1)
		return (PyObject *)PyErr_NoMemory();

	if ((z = newmpzobject()) == NULL)
		return NULL;

	mpz_div_2exp(&z->mpz, &a->mpz, mpz_get_ui(&b->mpz));
	return (PyObject *)z;
} /* mpz_rshift() */

static PyObject *
mpz_andfunc(mpzobject *a, mpzobject *b)
{
	mpzobject *z;


	if ((z = newmpzobject()) == NULL)
		return NULL;

	mpz_and(&z->mpz, &a->mpz, &b->mpz);
	return (PyObject *)z;
} /* mpz_andfunc() */

/* hack Hack HAck HACk HACK, XXX this code is dead slow */
void
mpz_xor(MP_INT *res, const MP_INT *op1, const MP_INT *op2)
{
	MP_INT tmpmpz;
	
	mpz_init(&tmpmpz);

	mpz_and(res, op1, op2);
	mpz_com(&tmpmpz, res);
	mpz_ior(res, op1, op2);
	mpz_and(res, res, &tmpmpz);

	mpz_clear(&tmpmpz);
} /* mpz_xor() HACK */

static PyObject *
mpz_xorfunc(mpzobject *a, mpzobject *b)
{
	mpzobject *z;


	if ((z = newmpzobject()) == NULL)
		return NULL;

	mpz_xor(&z->mpz, &a->mpz, &b->mpz);
	return (PyObject *)z;
} /* mpz_xorfunc() */

static PyObject *
mpz_orfunc(mpzobject *a, mpzobject *b)
{
	mpzobject *z;


	if ((z = newmpzobject()) == NULL)
		return NULL;

	mpz_ior(&z->mpz, &a->mpz, &b->mpz);
	return (PyObject *)z;
} /* mpz_orfunc() */

/* MPZ initialisation */

#include "longintrepr.h"

static PyObject *
MPZ_mpz(PyObject *self, PyObject *args)
{
	mpzobject *mpzp;
	PyObject *objp;


#ifdef MPZ_DEBUG
	fputs("MPZ_mpz() called...\n", stderr);
#endif /* def MPZ_DEBUG */

	if (!PyArg_Parse(args, "O", &objp))
		return NULL;

	/* at least we know it's some object */
	/* note DON't Py_DECREF args NEITHER objp */

	if (PyInt_Check(objp)) {
		long lval;

		if (!PyArg_Parse(objp, "l", &lval))
			return NULL;
		
		if (lval == (long)0) {
			Py_INCREF(mpz_value_zero);
			mpzp = mpz_value_zero;
		}
		else if (lval == (long)1) {
			Py_INCREF(mpz_value_one);
			mpzp = mpz_value_one;
		}			
		else if ((mpzp = newmpzobject()) == NULL)
			return NULL;
		else mpz_set_si(&mpzp->mpz, lval);
	}
	else if (PyLong_Check(objp)) {
		MP_INT mplongdigit;
		int i;
		unsigned char isnegative;
		

		if ((mpzp = newmpzobject()) == NULL)
			return NULL;

		mpz_set_si(&mpzp->mpz, 0L);
		mpz_init(&mplongdigit);
		
		/* how we're gonna handle this? */
		if ((isnegative =
		     ((i = ((PyLongObject *)objp)->ob_size) < 0) ))
			i = -i;

		while (i--) {
			mpz_set_ui(&mplongdigit,
				   (unsigned long)
				   ((PyLongObject *)objp)->ob_digit[i]);
			mpz_mul_2exp(&mplongdigit,&mplongdigit,
				     (unsigned long int)i * SHIFT);
			mpz_ior(&mpzp->mpz, &mpzp->mpz, &mplongdigit);
		}

		if (isnegative)
			mpz_neg(&mpzp->mpz, &mpzp->mpz);

		/* get rid of allocation for tmp variable */
		mpz_clear(&mplongdigit);
	}
	else if (PyString_Check(objp)) {
		unsigned char *cp = (unsigned char *)PyString_AS_STRING(objp);
		int len = PyString_GET_SIZE(objp);
		MP_INT mplongdigit;

		if ((mpzp = newmpzobject()) == NULL)
			return NULL;

		mpz_set_si(&mpzp->mpz, 0L);
		mpz_init(&mplongdigit);
		
		/* let's do it the same way as with the long conversion:
		   without thinking how it can be faster (-: :-) */

		cp += len;
		while (len--) {
			mpz_set_ui(&mplongdigit, (unsigned long)*--cp );
			mpz_mul_2exp(&mplongdigit,&mplongdigit,
				     (unsigned long int)len * 8);
			mpz_ior(&mpzp->mpz, &mpzp->mpz, &mplongdigit);
		}

		/* get rid of allocation for tmp variable */
		mpz_clear(&mplongdigit);
	}
	else if (is_mpzobject(objp)) {
		Py_INCREF(objp);
		mpzp = (mpzobject *)objp;
	}
	else {
		PyErr_SetString(PyExc_TypeError,
"mpz.mpz() expects integer, long, string or mpz object argument");
		return NULL;
	}


#ifdef MPZ_DEBUG
	fputs("MPZ_mpz: created mpz=", stderr);
	mpz_out_str(stderr, 10, &mpzp->mpz);
	putc('\n', stderr);
#endif /* def MPZ_DEBUG */
	return (PyObject *)mpzp;
} /* MPZ_mpz() */

static mpzobject *
mpz_mpzcoerce(PyObject *z)
{
	/* shortcut: 9 out of 10 times the type is already ok */
	if (is_mpzobject(z)) {
		Py_INCREF(z);
		return (mpzobject *)z;	/* coercion succeeded */
	}

	/* what types do we accept?: intobjects and longobjects */
	if (PyInt_Check(z) || PyLong_Check(z))
		return (mpzobject *)MPZ_mpz((PyObject *)NULL, z);

	PyErr_SetString(PyExc_TypeError,
			"number coercion (to mpzobject) failed");
	return NULL;
} /* mpz_mpzcoerce() */
	
/* Forward */
static void mpz_divm(MP_INT *res, const MP_INT *num,
	             const MP_INT *den, const MP_INT *mod);

static PyObject *
MPZ_powm(PyObject *self, PyObject *args)
{
	PyObject *base, *exp, *mod;
	mpzobject *mpzbase = NULL, *mpzexp = NULL, *mpzmod = NULL;
	mpzobject *z;
	int tstres;

	
	if (!PyArg_Parse(args, "(OOO)", &base, &exp, &mod))
		return NULL;

	if ((mpzbase = mpz_mpzcoerce(base)) == NULL
	    || (mpzexp = mpz_mpzcoerce(exp)) == NULL
	    || (mpzmod = mpz_mpzcoerce(mod)) == NULL
	    || (z = newmpzobject()) == NULL) {
		Py_XDECREF(mpzbase);
		Py_XDECREF(mpzexp);
		Py_XDECREF(mpzmod);
		return NULL;
	}

	if ((tstres=mpz_cmp_ui(&mpzexp->mpz, (unsigned long int)0)) == 0) {
		Py_INCREF(mpz_value_one);
		return (PyObject *)mpz_value_one;
	}

	if (tstres < 0) {
		MP_INT absexp;
		/* negative exp */

		mpz_init_set(&absexp, &mpzexp->mpz);
		mpz_abs(&absexp, &absexp);
		mpz_powm(&z->mpz, &mpzbase->mpz, &absexp, &mpzmod->mpz);

		mpz_divm(&z->mpz, &mpz_value_one->mpz, &z->mpz, &mpzmod->mpz);
		
		mpz_clear(&absexp);
	}
	else {
		mpz_powm(&z->mpz, &mpzbase->mpz, &mpzexp->mpz, &mpzmod->mpz);
	}
		
	Py_DECREF(mpzbase);
	Py_DECREF(mpzexp);
	Py_DECREF(mpzmod);

	return (PyObject *)z;
} /* MPZ_powm() */


static PyObject *
MPZ_gcd(PyObject *self, PyObject *args)
{
	PyObject *op1, *op2;
	mpzobject *mpzop1 = NULL, *mpzop2 = NULL;
	mpzobject *z;

	
	if (!PyArg_Parse(args, "(OO)", &op1, &op2))
		return NULL;

	if ((mpzop1 = mpz_mpzcoerce(op1)) == NULL
	    || (mpzop2 = mpz_mpzcoerce(op2)) == NULL
	    || (z = newmpzobject()) == NULL) {
		Py_XDECREF(mpzop1);
		Py_XDECREF(mpzop2);
		return NULL;
	}

	/* ok, we have three mpzobjects, and an initialised result holder */
	mpz_gcd(&z->mpz, &mpzop1->mpz, &mpzop2->mpz);

	Py_DECREF(mpzop1);
	Py_DECREF(mpzop2);

	return (PyObject *)z;
} /* MPZ_gcd() */


static PyObject *
MPZ_gcdext(PyObject *self, PyObject *args)
{
	PyObject *op1, *op2, *z = NULL;
	mpzobject *mpzop1 = NULL, *mpzop2 = NULL;
	mpzobject *g = NULL, *s = NULL, *t = NULL;

	
	if (!PyArg_Parse(args, "(OO)", &op1, &op2))
		return NULL;

	if ((mpzop1 = mpz_mpzcoerce(op1)) == NULL
	    || (mpzop2 = mpz_mpzcoerce(op2)) == NULL
	    || (z = PyTuple_New(3)) == NULL
	    || (g = newmpzobject()) == NULL
	    || (s = newmpzobject()) == NULL
	    || (t = newmpzobject()) == NULL) {
		Py_XDECREF(mpzop1);
		Py_XDECREF(mpzop2);
		Py_XDECREF(z);
		Py_XDECREF(g);
		Py_XDECREF(s);
		/*Py_XDECREF(t);*/
		return NULL;
	}

	mpz_gcdext(&g->mpz, &s->mpz, &t->mpz, &mpzop1->mpz, &mpzop2->mpz);

	Py_DECREF(mpzop1);
	Py_DECREF(mpzop2);

	(void)PyTuple_SetItem(z, 0, (PyObject *)g);
	(void)PyTuple_SetItem(z, 1, (PyObject *)s);
	(void)PyTuple_SetItem(z, 2, (PyObject *)t);

	return (PyObject *)z;
} /* MPZ_gcdext() */


static PyObject *
MPZ_sqrt(PyObject *self, PyObject *args)
{
	PyObject *op;
	mpzobject *mpzop = NULL;
	mpzobject *z;

	
	if (!PyArg_Parse(args, "O", &op))
		return NULL;

	if ((mpzop = mpz_mpzcoerce(op)) == NULL
	    || (z = newmpzobject()) == NULL) {
		Py_XDECREF(mpzop);
		return NULL;
	}

	mpz_sqrt(&z->mpz, &mpzop->mpz);

	Py_DECREF(mpzop);

	return (PyObject *)z;
} /* MPZ_sqrt() */


static PyObject *
MPZ_sqrtrem(PyObject *self, PyObject *args)
{
	PyObject *op, *z = NULL;
	mpzobject *mpzop = NULL;
	mpzobject *root = NULL, *rem = NULL;

	
	if (!PyArg_Parse(args, "O", &op))
		return NULL;

	if ((mpzop = mpz_mpzcoerce(op)) == NULL
	    || (z = PyTuple_New(2)) == NULL
	    || (root = newmpzobject()) == NULL
	    || (rem = newmpzobject()) == NULL) {
		Py_XDECREF(mpzop);
		Py_XDECREF(z);
		Py_XDECREF(root);
		/*Py_XDECREF(rem);*/
		return NULL;
	}

	mpz_sqrtrem(&root->mpz, &rem->mpz, &mpzop->mpz);

	Py_DECREF(mpzop);

	(void)PyTuple_SetItem(z, 0, (PyObject *)root);
	(void)PyTuple_SetItem(z, 1, (PyObject *)rem);

	return (PyObject *)z;
} /* MPZ_sqrtrem() */


static void
mpz_divm(MP_INT *res, const MP_INT *num, const MP_INT *den, const MP_INT *mod)
{
	MP_INT s0, s1, q, r, x, d0, d1;

	mpz_init_set(&s0, num);
	mpz_init_set_ui(&s1, 0);
	mpz_init(&q);
	mpz_init(&r);
	mpz_init(&x);
	mpz_init_set(&d0, den);
	mpz_init_set(&d1, mod);

#ifdef GMP2
	while (d1._mp_size != 0) {
#else
	while (d1.size != 0) {
#endif
		mpz_divmod(&q, &r, &d0, &d1);
		mpz_set(&d0, &d1);
		mpz_set(&d1, &r);

		mpz_mul(&x, &s1, &q);
		mpz_sub(&x, &s0, &x);
		mpz_set(&s0, &s1);
		mpz_set(&s1, &x);
	}

#ifdef GMP2
	if (d0._mp_size != 1 || d0._mp_d[0] != 1)
		res->_mp_size = 0; /* trouble: the gcd != 1; set s to zero */
#else
	if (d0.size != 1 || d0.d[0] != 1)
		res->size = 0;	/* trouble: the gcd != 1; set s to zero */
#endif
	else {
#ifdef MPZ_MDIV_BUG
		/* watch out here! first check the signs, and then perform
		   the mpz_mod() since mod could point to res */
		if ((s0.size < 0) != (mod->size < 0)) {
			mpz_mod(res, &s0, mod);

			if (res->size)
				mpz_add(res, res, mod);
		}
		else
			mpz_mod(res, &s0, mod);
		
#else /* def MPZ_MDIV_BUG */
		mpz_mmod(res, &s0, mod);
#endif /* def MPZ_MDIV_BUG else */
	}

	mpz_clear(&s0);
	mpz_clear(&s1);
	mpz_clear(&q);
	mpz_clear(&r);
	mpz_clear(&x);
	mpz_clear(&d0);
	mpz_clear(&d1);
} /* mpz_divm() */


static PyObject *
MPZ_divm(PyObject *self, PyObject *args)
{
	PyObject *num, *den, *mod;
	mpzobject *mpznum, *mpzden = NULL, *mpzmod = NULL;
	mpzobject *z = NULL;

	
	if (!PyArg_Parse(args, "(OOO)", &num, &den, &mod))
		return NULL;

	if ((mpznum = mpz_mpzcoerce(num)) == NULL
	    || (mpzden = mpz_mpzcoerce(den)) == NULL
	    || (mpzmod = mpz_mpzcoerce(mod)) == NULL
	    || (z = newmpzobject()) == NULL ) {
		Py_XDECREF(mpznum);
		Py_XDECREF(mpzden);
		Py_XDECREF(mpzmod);
		return NULL;
	}
	
	mpz_divm(&z->mpz, &mpznum->mpz, &mpzden->mpz, &mpzmod->mpz);

	Py_DECREF(mpznum);
	Py_DECREF(mpzden);
	Py_DECREF(mpzmod);

	if (mpz_cmp_ui(&z->mpz, (unsigned long int)0) == 0) {
		Py_DECREF(z);
		PyErr_SetString(PyExc_ValueError,
				"gcd(den, mod) != 1 or num == 0");
		return NULL;
	}

	return (PyObject *)z;
} /* MPZ_divm() */


/* MPZ methods-as-attributes */
#ifdef MPZ_CONVERSIONS_AS_METHODS
static PyObject *
mpz_int(mpzobject *self, PyObject *args)
#else /* def MPZ_CONVERSIONS_AS_METHODS */
static PyObject *
mpz_int(mpzobject *self)
#endif /* def MPZ_CONVERSIONS_AS_METHODS else */
{
	long sli;


#ifdef MPZ_CONVERSIONS_AS_METHODS
	if (!PyArg_NoArgs(args))
		return NULL;
#endif /* def MPZ_CONVERSIONS_AS_METHODS */

	if (mpz_size(&self->mpz) > 1
	    || (sli = (long)mpz_get_ui(&self->mpz)) < (long)0 ) {
		PyErr_SetString(PyExc_ValueError,
				"mpz.int() arg too long to convert");
		return NULL;
	}

	if (mpz_cmp_ui(&self->mpz, (unsigned long)0) < 0)
		sli = -sli;

	return PyInt_FromLong(sli);
} /* mpz_int() */
	
static PyObject *
#ifdef MPZ_CONVERSIONS_AS_METHODS
mpz_long(mpzobject *self, PyObject *args)
#else /* def MPZ_CONVERSIONS_AS_METHODS */
mpz_long(mpzobject *self)
#endif /* def MPZ_CONVERSIONS_AS_METHODS else */
{
	int i, isnegative;
	unsigned long int uli;
	PyLongObject *longobjp;
	int ldcount;
	int bitpointer, newbitpointer;
	MP_INT mpzscratch;


#ifdef MPZ_CONVERSIONS_AS_METHODS
	if (!PyArg_NoArgs(args))
		return NULL;
#endif /* def MPZ_CONVERSIONS_AS_METHODS */

	/* determine length of python-long to be allocated */
	if ((longobjp = _PyLong_New(i = (int)
			    ((mpz_size(&self->mpz) * BITS_PER_MP_LIMB
			      + SHIFT - 1) /
			     SHIFT))) == NULL)
		return NULL;

	/* determine sign, and copy self to scratch var */
	mpz_init_set(&mpzscratch, &self->mpz);
	if ((isnegative = (mpz_cmp_ui(&self->mpz, (unsigned long int)0) < 0)))
		mpz_neg(&mpzscratch, &mpzscratch);

	/* let those bits come, let those bits go,
	   e.g. dismantle mpzscratch, build PyLongObject */

	bitpointer = 0;		/* the number of valid bits in stock */
	newbitpointer = 0;
	ldcount = 0;		/* the python-long limb counter */
	uli = (unsigned long int)0;
	while (i--) {
		longobjp->ob_digit[ldcount] = uli & MASK;

		/* check if we've had enough bits for this digit */
		if (bitpointer < SHIFT) {
			uli = mpz_get_ui(&mpzscratch);
			longobjp->ob_digit[ldcount] |=
				(uli << bitpointer) & MASK;
			uli >>= SHIFT-bitpointer;
			bitpointer += BITS_PER_MP_LIMB;
			mpz_div_2exp(&mpzscratch, &mpzscratch,
				     BITS_PER_MP_LIMB);
		}
		else
			uli >>= SHIFT;
		bitpointer -= SHIFT;
		ldcount++;
	}

	assert(mpz_cmp_ui(&mpzscratch, (unsigned long int)0) == 0);
	mpz_clear(&mpzscratch);
	assert(ldcount <= longobjp->ob_size);

	/* long_normalize() is file-static */
	/* longobjp = long_normalize(longobjp); */
	while (ldcount > 0 && longobjp->ob_digit[ldcount-1] == 0)
		ldcount--;
	longobjp->ob_size = ldcount;
	

	if (isnegative)
		longobjp->ob_size = -longobjp->ob_size;

	return (PyObject *)longobjp;
	
} /* mpz_long() */


/* I would have avoided pow() anyways, so ... */
static const double multiplier = 256.0 * 256.0 * 256.0 * 256.0;
	
#ifdef MPZ_CONVERSIONS_AS_METHODS
static PyObject *
mpz_float(mpzobject *self, PyObject *args)
#else /* def MPZ_CONVERSIONS_AS_METHODS */
static PyObject *
mpz_float(mpzobject *self)
#endif /* def MPZ_CONVERSIONS_AS_METHODS else */
{
	int i, isnegative;
	double x;
	double mulstate;
	MP_INT mpzscratch;


#ifdef MPZ_CONVERSIONS_AS_METHODS
	if (!PyArg_NoArgs(args))
		return NULL;
#endif /* def MPZ_CONVERSIONS_AS_METHODS */

	i = (int)mpz_size(&self->mpz);
	
	/* determine sign, and copy abs(self) to scratch var */
	if ((isnegative = (mpz_cmp_ui(&self->mpz, (unsigned long int)0) < 0)))
	{
		mpz_init(&mpzscratch);
		mpz_neg(&mpzscratch, &self->mpz);
	}
	else
		mpz_init_set(&mpzscratch, &self->mpz);

	/* let those bits come, let those bits go,
	   e.g. dismantle mpzscratch, build PyFloatObject */

	/* Can this overflow?  Dunno, protect against that possibility. */
	PyFPE_START_PROTECT("mpz_float", return 0)
	x = 0.0;
	mulstate = 1.0;
	while (i--) {
		x += mulstate * mpz_get_ui(&mpzscratch);
		mulstate *= multiplier;
		mpz_div_2exp(&mpzscratch, &mpzscratch, BITS_PER_MP_LIMB);
	}
	PyFPE_END_PROTECT(mulstate)

	assert(mpz_cmp_ui(&mpzscratch, (unsigned long int)0) == 0);
	mpz_clear(&mpzscratch);

	if (isnegative)
		x = -x;

	return PyFloat_FromDouble(x);
	
} /* mpz_float() */

#ifdef MPZ_CONVERSIONS_AS_METHODS
static PyObject *
mpz_hex(mpzobject *self, PyObject *args)
#else /* def MPZ_CONVERSIONS_AS_METHODS */
static PyObject *
mpz_hex(mpzobject *self)
#endif /* def MPZ_CONVERSIONS_AS_METHODS else */
{
#ifdef MPZ_CONVERSIONS_AS_METHODS
	if (!PyArg_NoArgs(args))
		return NULL;
#endif /* def MPZ_CONVERSIONS_AS_METHODS */
	
	return mpz_format((PyObject *)self, 16, (unsigned char)1);
} /* mpz_hex() */
	
#ifdef MPZ_CONVERSIONS_AS_METHODS
static PyObject *
mpz_oct(mpzobject *self, PyObject *args)
#else /* def MPZ_CONVERSIONS_AS_METHODS */
static PyObject *
mpz_oct(mpzobject *self)
#endif /* def MPZ_CONVERSIONS_AS_METHODS else */
{
#ifdef MPZ_CONVERSIONS_AS_METHODS
	if (!PyArg_NoArgs(args))
		return NULL;
#endif /* def MPZ_CONVERSIONS_AS_METHODS */
	
	return mpz_format((PyObject *)self, 8, (unsigned char)1);
} /* mpz_oct() */
	
static PyObject *
mpz_binary(mpzobject *self, PyObject *args)
{
	int size;
	PyStringObject *strobjp;
	char *cp;
	MP_INT mp;
	unsigned long ldigit;
	
	if (!PyArg_NoArgs(args))
		return NULL;

	if (mpz_cmp_ui(&self->mpz, (unsigned long int)0) < 0) {
		PyErr_SetString(PyExc_ValueError,
				"mpz.binary() arg must be >= 0");
		return NULL;
	}

	mpz_init_set(&mp, &self->mpz);
	size = (int)mpz_size(&mp);

	if ((strobjp = (PyStringObject *)
	     PyString_FromStringAndSize(
		     (char *)0, size * sizeof (unsigned long int))) == NULL)
		return NULL;

	/* get the beginning of the string memory and start copying things */
	cp = PyString_AS_STRING(strobjp);

	/* this has been programmed using a (fairly) decent lib-i/f it could
	   be must faster if we looked into the GMP lib */
	while (size--) {
		ldigit = mpz_get_ui(&mp);
		mpz_div_2exp(&mp, &mp, BITS_PER_MP_LIMB);
		*cp++ = (unsigned char)(ldigit & 0xFF);
		*cp++ = (unsigned char)((ldigit >>= 8) & 0xFF);
		*cp++ = (unsigned char)((ldigit >>= 8) & 0xFF);
		*cp++ = (unsigned char)((ldigit >>= 8) & 0xFF);
	}

	while (strobjp->ob_size && !*--cp)
		strobjp->ob_size--;

	return (PyObject *)strobjp;
} /* mpz_binary() */
	

static PyMethodDef mpz_methods[] = {
#ifdef MPZ_CONVERSIONS_AS_METHODS
	{"int",			mpz_int},
	{"long",		mpz_long},
	{"float",		mpz_float},
	{"hex",			mpz_hex},
	{"oct",			mpz_oct},
#endif /* def MPZ_CONVERSIONS_AS_METHODS */
	{"binary",		(PyCFunction)mpz_binary},
	{NULL,			NULL}		/* sentinel */
};

static PyObject *
mpz_getattr(mpzobject *self, char *name)
{
	return Py_FindMethod(mpz_methods, (PyObject *)self, name);
} /* mpz_getattr() */


static int
mpz_coerce(PyObject **pv, PyObject **pw)
{
	PyObject *z;

#ifdef MPZ_DEBUG
	fputs("mpz_coerce() called...\n", stderr);
#endif /* def MPZ_DEBUG */

	assert(is_mpzobject(*pv));

	/* always convert other arg to mpz value, except for floats */
	if (!PyFloat_Check(*pw)) {
		if ((z = (PyObject *)mpz_mpzcoerce(*pw)) == NULL)
			return -1;	/* -1: an error always has been set */
		
		Py_INCREF(*pv);
		*pw = z;
	}
	else {
#ifdef MPZ_CONVERSIONS_AS_METHODS
		if ((z = mpz_float((mpzobject *)(*pv), NULL)) == NULL)
			return -1;
#else /* def MPZ_CONVERSIONS_AS_METHODS */
		if ((z = mpz_float((mpzobject *)(*pv))) == NULL)
			return -1;
#endif /* def MPZ_CONVERSIONS_AS_METHODS else */

		Py_INCREF(*pw);
		*pv = z;
	}
	return 0;		/* coercion succeeded */

} /* mpz_coerce() */


static PyObject *
mpz_repr(PyObject *v)
{
	return mpz_format(v, 10, (unsigned char)1);
} /* mpz_repr() */



#define UF (unaryfunc)
#define BF (binaryfunc)
#define TF (ternaryfunc)
#define IF (inquiry)
#define CF (coercion)

static PyNumberMethods mpz_as_number = {
	BF mpz_addition,	/*nb_add*/
	BF mpz_substract,	/*nb_subtract*/
	BF mpz_multiply,	/*nb_multiply*/
	BF mpz_divide,		/*nb_divide*/
	BF mpz_remainder,	/*nb_remainder*/
	BF mpz_div_and_mod,	/*nb_divmod*/
	TF mpz_power,		/*nb_power*/
	UF mpz_negative,	/*nb_negative*/
	UF mpz_positive,	/*tp_positive*/
	UF mpz_absolute,	/*tp_absolute*/
	IF mpz_nonzero,		/*tp_nonzero*/
	UF py_mpz_invert,	/*nb_invert*/
	BF mpz_lshift,		/*nb_lshift*/
	BF mpz_rshift,		/*nb_rshift*/
	BF mpz_andfunc,		/*nb_and*/
	BF mpz_xorfunc,		/*nb_xor*/
	BF mpz_orfunc,		/*nb_or*/
	CF mpz_coerce,		/*nb_coerce*/
#ifndef MPZ_CONVERSIONS_AS_METHODS
	UF mpz_int,		/*nb_int*/
	UF mpz_long,		/*nb_long*/
	UF mpz_float,		/*nb_float*/
	UF mpz_oct,		/*nb_oct*/
	UF mpz_hex,		/*nb_hex*/
#endif /* ndef MPZ_CONVERSIONS_AS_METHODS */
};

static PyTypeObject MPZtype = {
	PyObject_HEAD_INIT(&PyType_Type)
	0,			/*ob_size*/
	"mpz",			/*tp_name*/
	sizeof(mpzobject),	/*tp_size*/
	0,			/*tp_itemsize*/
	/* methods */
	(destructor)mpz_dealloc, /*tp_dealloc*/
	0,			/*tp_print*/
	(getattrfunc)mpz_getattr, /*tp_getattr*/
	0,			/*tp_setattr*/
	(cmpfunc)mpz_compare,	/*tp_compare*/
	(reprfunc)mpz_repr,	/*tp_repr*/
        &mpz_as_number, 	/*tp_as_number*/
};

/* List of functions exported by this module */

static PyMethodDef mpz_functions[] = {
#if 0
	{initialiser_name,	MPZ_mpz},
#else /* 0 */
	/* until guido ``fixes'' struct PyMethodDef */
	{(char *)initialiser_name,	MPZ_mpz},
#endif /* 0 else */	
	{"powm",		MPZ_powm},
	{"gcd",			MPZ_gcd},
	{"gcdext",		MPZ_gcdext},
	{"sqrt",		MPZ_sqrt},
	{"sqrtrem",		MPZ_sqrtrem},
	{"divm",		MPZ_divm},
	{NULL,			NULL}		 /* Sentinel */
};


/* #define MP_TEST_ALLOC */

#ifdef MP_TEST_ALLOC
#define MP_TEST_SIZE		4
static const char mp_test_magic[MP_TEST_SIZE] = {'\xAA','\xAA','\xAA','\xAA'};
static mp_test_error(int *location)
{
	/* assumptions: *alloc returns address divisible by 4,
	mpz_* routines allocate in chunks divisible by four */
	fprintf(stderr, "MP_TEST_ERROR: location holds 0x%08d\n", *location );
	Py_FatalError("MP_TEST_ERROR");
} /* static mp_test_error() */
#define MP_EXTRA_ALLOC(size)	((size) + MP_TEST_SIZE)
#define MP_SET_TEST(basep,size)	(void)memcpy( ((char *)(basep))+(size), mp_test_magic, MP_TEST_SIZE)
#define MP_DO_TEST(basep,size)	if ( !memcmp( ((char *)(basep))+(size), mp_test_magic, MP_TEST_SIZE ) ) \
					; \
				else \
					mp_test_error((int *)((char *)(basep) + size))
#else /* def MP_TEST_ALLOC */
#define MP_EXTRA_ALLOC(size)	(size)
#define MP_SET_TEST(basep,size)
#define MP_DO_TEST(basep,size)
#endif /* def MP_TEST_ALLOC else */

void *mp_allocate(size_t alloc_size)
{
	void *res;

#ifdef MPZ_DEBUG
	fprintf(stderr, "mp_allocate  :                             size %ld\n",
		alloc_size);
#endif /* def MPZ_DEBUG */	

	if ( (res = malloc(MP_EXTRA_ALLOC(alloc_size))) == NULL )
		Py_FatalError("mp_allocate failure");

#ifdef MPZ_DEBUG
	fprintf(stderr, "mp_allocate  :     address %08p\n", res);
#endif /* def MPZ_DEBUG */	

	MP_SET_TEST(res,alloc_size);
	
	return res;
} /* mp_allocate() */


void *mp_reallocate(void *ptr, size_t old_size, size_t new_size)
{
	void *res;

#ifdef MPZ_DEBUG
	fprintf(stderr, "mp_reallocate: old address %08p, old size %ld\n",
		ptr, old_size);
#endif /* def MPZ_DEBUG */	

	MP_DO_TEST(ptr, old_size);
	
	if ( (res = realloc(ptr, MP_EXTRA_ALLOC(new_size))) == NULL )
		Py_FatalError("mp_reallocate failure");

#ifdef MPZ_DEBUG
	fprintf(stderr, "mp_reallocate: new address %08p, new size %ld\n",
		res, new_size);
#endif /* def MPZ_DEBUG */	

	MP_SET_TEST(res, new_size);

	return res;
} /* mp_reallocate() */


void mp_free(void *ptr, size_t size)
{

#ifdef MPZ_DEBUG
	fprintf(stderr, "mp_free      : old address %08p, old size %ld\n",
		ptr, size);
#endif /* def MPZ_DEBUG */	

	MP_DO_TEST(ptr, size);
	free(ptr);
} /* mp_free() */



/* Initialize this module. */

DL_EXPORT(void)
initmpz(void)
{
	PyObject *module;
	PyObject *dict;

#ifdef MPZ_DEBUG
	fputs( "initmpz() called...\n", stderr );
#endif /* def MPZ_DEBUG */

	mp_set_memory_functions( mp_allocate, mp_reallocate, mp_free );
	module = Py_InitModule("mpz", mpz_functions);

	/* create some frequently used constants */
	if ((mpz_value_zero = newmpzobject()) == NULL)
		goto finally;
	mpz_set_ui(&mpz_value_zero->mpz, (unsigned long int)0);

	if ((mpz_value_one = newmpzobject()) == NULL)
		goto finally;
	mpz_set_ui(&mpz_value_one->mpz, (unsigned long int)1);

	if ((mpz_value_mone = newmpzobject()) == NULL)
		goto finally;
	mpz_set_si(&mpz_value_mone->mpz, (long)-1);

	dict = PyModule_GetDict(module);
	if (dict != NULL) {
		PyDict_SetItemString(dict, "MPZType", (PyObject*)&MPZtype);
	}
  finally:
	return;
} /* initmpz() */

#ifdef MAKEDUMMYINT
int _mpz_dummy_int;	/* XXX otherwise, we're .bss-less (DYNLOAD->Jack?) */
#endif /* def MAKEDUMMYINT */
