/* struct module -- pack values into and (out of) bytes objects */

/* New version supporting byte order, alignment and size options,
   character strings, and unsigned numbers */

#define PY_SSIZE_T_CLEAN

#include "Python.h"
#include "structseq.h"
#include "structmember.h"
#include <ctype.h>

static PyTypeObject PyStructType;

/* If PY_STRUCT_OVERFLOW_MASKING is defined, the struct module will wrap all input
   numbers for explicit endians such that they fit in the given type, much
   like explicit casting in C. A warning will be raised if the number did
   not originally fit within the range of the requested type. If it is
   not defined, then all range errors and overflow will be struct.error
   exceptions. */

#define PY_STRUCT_OVERFLOW_MASKING 1

#ifdef PY_STRUCT_OVERFLOW_MASKING
static PyObject *pylong_ulong_mask = NULL;
static PyObject *pyint_zero = NULL;
#endif

/* If PY_STRUCT_FLOAT_COERCE is defined, the struct module will allow float
   arguments for integer formats with a warning for backwards
   compatibility. */

#define PY_STRUCT_FLOAT_COERCE 1

#ifdef PY_STRUCT_FLOAT_COERCE
#define FLOAT_COERCE "integer argument expected, got float"
#endif


/* The translation function for each format character is table driven */
typedef struct _formatdef {
	char format;
	Py_ssize_t size;
	Py_ssize_t alignment;
	PyObject* (*unpack)(const char *,
			    const struct _formatdef *);
	int (*pack)(char *, PyObject *,
		    const struct _formatdef *);
} formatdef;

typedef struct _formatcode {
	const struct _formatdef *fmtdef;
	Py_ssize_t offset;
	Py_ssize_t size;
} formatcode;

/* Struct object interface */

typedef struct {
	PyObject_HEAD
	Py_ssize_t s_size;
	Py_ssize_t s_len;
	formatcode *s_codes;
	PyObject *s_format;
	PyObject *weakreflist; /* List of weak references */
} PyStructObject;


#define PyStruct_Check(op) PyObject_TypeCheck(op, &PyStructType)
#define PyStruct_CheckExact(op) (Py_TYPE(op) == &PyStructType)


/* Exception */

static PyObject *StructError;


/* Define various structs to figure out the alignments of types */


typedef struct { char c; short x; } st_short;
typedef struct { char c; int x; } st_int;
typedef struct { char c; long x; } st_long;
typedef struct { char c; float x; } st_float;
typedef struct { char c; double x; } st_double;
typedef struct { char c; void *x; } st_void_p;

#define SHORT_ALIGN (sizeof(st_short) - sizeof(short))
#define INT_ALIGN (sizeof(st_int) - sizeof(int))
#define LONG_ALIGN (sizeof(st_long) - sizeof(long))
#define FLOAT_ALIGN (sizeof(st_float) - sizeof(float))
#define DOUBLE_ALIGN (sizeof(st_double) - sizeof(double))
#define VOID_P_ALIGN (sizeof(st_void_p) - sizeof(void *))

/* We can't support q and Q in native mode unless the compiler does;
   in std mode, they're 8 bytes on all platforms. */
#ifdef HAVE_LONG_LONG
typedef struct { char c; PY_LONG_LONG x; } s_long_long;
#define LONG_LONG_ALIGN (sizeof(s_long_long) - sizeof(PY_LONG_LONG))
#endif

#ifdef HAVE_C99_BOOL
#define BOOL_TYPE _Bool
typedef struct { char c; _Bool x; } s_bool;
#define BOOL_ALIGN (sizeof(s_bool) - sizeof(BOOL_TYPE))
#else
#define BOOL_TYPE char
#define BOOL_ALIGN 0
#endif

#define STRINGIFY(x)    #x

#ifdef __powerc
#pragma options align=reset
#endif

/* Helper to get a PyLongObject by hook or by crook.  Caller should decref. */

static PyObject *
get_pylong(PyObject *v)
{
	PyNumberMethods *m;

	assert(v != NULL);
	if (PyLong_Check(v)) {
		Py_INCREF(v);
		return v;
	}
	m = Py_TYPE(v)->tp_as_number;
	if (m != NULL && m->nb_long != NULL) {
		v = m->nb_long(v);
		if (v == NULL)
			return NULL;
		if (PyLong_Check(v))
			return v;
		Py_DECREF(v);
	}
	PyErr_SetString(StructError,
			"cannot convert argument to long");
	return NULL;
}

/* Helper routine to get a Python integer and raise the appropriate error
   if it isn't one */

static int
get_long(PyObject *v, long *p)
{
	long x = PyLong_AsLong(v);
	if (x == -1 && PyErr_Occurred()) {
#ifdef PY_STRUCT_FLOAT_COERCE
		if (PyFloat_Check(v)) {
			PyObject *o;
			int res;
			PyErr_Clear();
			if (PyErr_WarnEx(PyExc_DeprecationWarning, FLOAT_COERCE, 2) < 0)
				return -1;
			o = PyNumber_Int(v);
			if (o == NULL)
				return -1;
			res = get_long(o, p);
			Py_DECREF(o);
			return res;
		}
#endif
		if (PyErr_ExceptionMatches(PyExc_TypeError))
			PyErr_SetString(StructError,
					"required argument is not an integer");
		return -1;
	}
	*p = x;
	return 0;
}


/* Same, but handling unsigned long */

static int
get_ulong(PyObject *v, unsigned long *p)
{
	if (PyLong_Check(v)) {
		unsigned long x = PyLong_AsUnsignedLong(v);
		if (x == (unsigned long)(-1) && PyErr_Occurred())
			return -1;
		*p = x;
		return 0;
	}
	if (get_long(v, (long *)p) < 0)
		return -1;
	if (((long)*p) < 0) {
		PyErr_SetString(StructError,
				"unsigned argument is < 0");
		return -1;
	}
	return 0;
}

#ifdef HAVE_LONG_LONG

/* Same, but handling native long long. */

static int
get_longlong(PyObject *v, PY_LONG_LONG *p)
{
	PY_LONG_LONG x;

	v = get_pylong(v);
	if (v == NULL)
		return -1;
	assert(PyLong_Check(v));
	x = PyLong_AsLongLong(v);
	Py_DECREF(v);
	if (x == (PY_LONG_LONG)-1 && PyErr_Occurred())
		return -1;
	*p = x;
	return 0;
}

/* Same, but handling native unsigned long long. */

static int
get_ulonglong(PyObject *v, unsigned PY_LONG_LONG *p)
{
	unsigned PY_LONG_LONG x;

	v = get_pylong(v);
	if (v == NULL)
		return -1;
	assert(PyLong_Check(v));
	x = PyLong_AsUnsignedLongLong(v);
	Py_DECREF(v);
	if (x == (unsigned PY_LONG_LONG)-1 && PyErr_Occurred())
		return -1;
	*p = x;
	return 0;
}

#endif

#ifdef PY_STRUCT_OVERFLOW_MASKING

/* Helper routine to get a Python integer and raise the appropriate error
   if it isn't one */

#define INT_OVERFLOW "struct integer overflow masking is deprecated"

static int
get_wrapped_long(PyObject *v, long *p)
{
	if (get_long(v, p) < 0) {
		if (PyLong_Check(v) &&
		    PyErr_ExceptionMatches(PyExc_OverflowError)) {
			PyObject *wrapped;
			long x;
			PyErr_Clear();
#ifdef PY_STRUCT_FLOAT_COERCE
			if (PyFloat_Check(v)) {
				PyObject *o;
				int res;
				PyErr_Clear();
				if (PyErr_WarnEx(PyExc_DeprecationWarning, FLOAT_COERCE, 2) < 0)
					return -1;
				o = PyNumber_Int(v);
				if (o == NULL)
					return -1;
				res = get_wrapped_long(o, p);
				Py_DECREF(o);
				return res;
			}
#endif
			if (PyErr_WarnEx(PyExc_DeprecationWarning, INT_OVERFLOW, 2) < 0)
				return -1;
			wrapped = PyNumber_And(v, pylong_ulong_mask);
			if (wrapped == NULL)
				return -1;
			x = (long)PyLong_AsUnsignedLong(wrapped);
			Py_DECREF(wrapped);
			if (x == -1 && PyErr_Occurred())
				return -1;
			*p = x;
		} else {
			return -1;
		}
	}
	return 0;
}

static int
get_wrapped_ulong(PyObject *v, unsigned long *p)
{
	long x = (long)PyLong_AsUnsignedLong(v);
	if (x == -1 && PyErr_Occurred()) {
		PyObject *wrapped;
		PyErr_Clear();
#ifdef PY_STRUCT_FLOAT_COERCE
		if (PyFloat_Check(v)) {
			PyObject *o;
			int res;
			PyErr_Clear();
			if (PyErr_WarnEx(PyExc_DeprecationWarning, FLOAT_COERCE, 2) < 0)
				return -1;
			o = PyNumber_Int(v);
			if (o == NULL)
				return -1;
			res = get_wrapped_ulong(o, p);
			Py_DECREF(o);
			return res;
		}
#endif
		wrapped = PyNumber_And(v, pylong_ulong_mask);
		if (wrapped == NULL)
			return -1;
		if (PyErr_WarnEx(PyExc_DeprecationWarning, INT_OVERFLOW, 2) < 0) {
			Py_DECREF(wrapped);
			return -1;
		}
		x = (long)PyLong_AsUnsignedLong(wrapped);
		Py_DECREF(wrapped);
		if (x == -1 && PyErr_Occurred())
			return -1;
	}
	*p = (unsigned long)x;
	return 0;
}

#define RANGE_ERROR(x, f, flag, mask) \
	do { \
		if (_range_error(f, flag) < 0) \
			return -1; \
		else \
			(x) &= (mask); \
	} while (0)

#else

#define get_wrapped_long get_long
#define get_wrapped_ulong get_ulong
#define RANGE_ERROR(x, f, flag, mask) return _range_error(f, flag)

#endif

/* Floating point helpers */

static PyObject *
unpack_float(const char *p,  /* start of 4-byte string */
             int le)	     /* true for little-endian, false for big-endian */
{
	double x;

	x = _PyFloat_Unpack4((unsigned char *)p, le);
	if (x == -1.0 && PyErr_Occurred())
		return NULL;
	return PyFloat_FromDouble(x);
}

static PyObject *
unpack_double(const char *p,  /* start of 8-byte string */
              int le)         /* true for little-endian, false for big-endian */
{
	double x;

	x = _PyFloat_Unpack8((unsigned char *)p, le);
	if (x == -1.0 && PyErr_Occurred())
		return NULL;
	return PyFloat_FromDouble(x);
}

/* Helper to format the range error exceptions */
static int
_range_error(const formatdef *f, int is_unsigned)
{
	/* ulargest is the largest unsigned value with f->size bytes.
	 * Note that the simpler:
	 *     ((size_t)1 << (f->size * 8)) - 1
	 * doesn't work when f->size == sizeof(size_t) because C doesn't
	 * define what happens when a left shift count is >= the number of
	 * bits in the integer being shifted; e.g., on some boxes it doesn't
	 * shift at all when they're equal.
	 */
	const size_t ulargest = (size_t)-1 >> ((SIZEOF_SIZE_T - f->size)*8);
	assert(f->size >= 1 && f->size <= SIZEOF_SIZE_T);
	if (is_unsigned)
		PyErr_Format(StructError,
			"'%c' format requires 0 <= number <= %zu",
			f->format,
			ulargest);
	else {
		const Py_ssize_t largest = (Py_ssize_t)(ulargest >> 1);
		PyErr_Format(StructError,
			"'%c' format requires %zd <= number <= %zd",
			f->format,
			~ largest,
			largest);
	}
#ifdef PY_STRUCT_OVERFLOW_MASKING
	{
		PyObject *ptype, *pvalue, *ptraceback;
		PyObject *msg;
		int rval;
		PyErr_Fetch(&ptype, &pvalue, &ptraceback);
		assert(pvalue != NULL);
		msg = PyObject_Str(pvalue);
		Py_XDECREF(ptype);
		Py_XDECREF(pvalue);
		Py_XDECREF(ptraceback);
		if (msg == NULL)
			return -1;
		rval = PyErr_WarnEx(PyExc_DeprecationWarning,
				    PyUnicode_AsString(msg), 2);
		Py_DECREF(msg);
		if (rval == 0)
			return 0;
	}
#endif
	return -1;
}



/* A large number of small routines follow, with names of the form

   [bln][up]_TYPE

   [bln] distiguishes among big-endian, little-endian and native.
   [pu] distiguishes between pack (to struct) and unpack (from struct).
   TYPE is one of char, byte, ubyte, etc.
*/

/* Native mode routines. ****************************************************/
/* NOTE:
   In all n[up]_<type> routines handling types larger than 1 byte, there is
   *no* guarantee that the p pointer is properly aligned for each type,
   therefore memcpy is called.  An intermediate variable is used to
   compensate for big-endian architectures.
   Normally both the intermediate variable and the memcpy call will be
   skipped by C optimisation in little-endian architectures (gcc >= 2.91
   does this). */

static PyObject *
nu_char(const char *p, const formatdef *f)
{
	return PyBytes_FromStringAndSize(p, 1);
}

static PyObject *
nu_byte(const char *p, const formatdef *f)
{
	return PyLong_FromLong((long) *(signed char *)p);
}

static PyObject *
nu_ubyte(const char *p, const formatdef *f)
{
	return PyLong_FromLong((long) *(unsigned char *)p);
}

static PyObject *
nu_short(const char *p, const formatdef *f)
{
	short x;
	memcpy((char *)&x, p, sizeof x);
	return PyLong_FromLong((long)x);
}

static PyObject *
nu_ushort(const char *p, const formatdef *f)
{
	unsigned short x;
	memcpy((char *)&x, p, sizeof x);
	return PyLong_FromLong((long)x);
}

static PyObject *
nu_int(const char *p, const formatdef *f)
{
	int x;
	memcpy((char *)&x, p, sizeof x);
	return PyLong_FromLong((long)x);
}

static PyObject *
nu_uint(const char *p, const formatdef *f)
{
	unsigned int x;
	memcpy((char *)&x, p, sizeof x);
#if (SIZEOF_LONG > SIZEOF_INT)
	return PyLong_FromLong((long)x);
#else
	if (x <= ((unsigned int)LONG_MAX))
		return PyLong_FromLong((long)x);
	return PyLong_FromUnsignedLong((unsigned long)x);
#endif
}

static PyObject *
nu_long(const char *p, const formatdef *f)
{
	long x;
	memcpy((char *)&x, p, sizeof x);
	return PyLong_FromLong(x);
}

static PyObject *
nu_ulong(const char *p, const formatdef *f)
{
	unsigned long x;
	memcpy((char *)&x, p, sizeof x);
	if (x <= LONG_MAX)
		return PyLong_FromLong((long)x);
	return PyLong_FromUnsignedLong(x);
}

/* Native mode doesn't support q or Q unless the platform C supports
   long long (or, on Windows, __int64). */

#ifdef HAVE_LONG_LONG

static PyObject *
nu_longlong(const char *p, const formatdef *f)
{
	PY_LONG_LONG x;
	memcpy((char *)&x, p, sizeof x);
	if (x >= LONG_MIN && x <= LONG_MAX)
		return PyLong_FromLong(Py_SAFE_DOWNCAST(x, PY_LONG_LONG, long));
	return PyLong_FromLongLong(x);
}

static PyObject *
nu_ulonglong(const char *p, const formatdef *f)
{
	unsigned PY_LONG_LONG x;
	memcpy((char *)&x, p, sizeof x);
	if (x <= LONG_MAX)
		return PyLong_FromLong(Py_SAFE_DOWNCAST(x, unsigned PY_LONG_LONG, long));
	return PyLong_FromUnsignedLongLong(x);
}

#endif

static PyObject *
nu_bool(const char *p, const formatdef *f)
{
	BOOL_TYPE x;
	memcpy((char *)&x, p, sizeof x);
	return PyBool_FromLong(x != 0);
}


static PyObject *
nu_float(const char *p, const formatdef *f)
{
	float x;
	memcpy((char *)&x, p, sizeof x);
	return PyFloat_FromDouble((double)x);
}

static PyObject *
nu_double(const char *p, const formatdef *f)
{
	double x;
	memcpy((char *)&x, p, sizeof x);
	return PyFloat_FromDouble(x);
}

static PyObject *
nu_void_p(const char *p, const formatdef *f)
{
	void *x;
	memcpy((char *)&x, p, sizeof x);
	return PyLong_FromVoidPtr(x);
}

static int
np_byte(char *p, PyObject *v, const formatdef *f)
{
	long x;
	if (get_long(v, &x) < 0)
		return -1;
	if (x < -128 || x > 127){
		PyErr_SetString(StructError,
				"byte format requires -128 <= number <= 127");
		return -1;
	}
	*p = (char)x;
	return 0;
}

static int
np_ubyte(char *p, PyObject *v, const formatdef *f)
{
	long x;
	if (get_long(v, &x) < 0)
		return -1;
	if (x < 0 || x > 255){
		PyErr_SetString(StructError,
				"ubyte format requires 0 <= number <= 255");
		return -1;
	}
	*p = (char)x;
	return 0;
}

static int
np_char(char *p, PyObject *v, const formatdef *f)
{
	if (PyUnicode_Check(v)) {
		v = _PyUnicode_AsDefaultEncodedString(v, NULL);
		if (v == NULL)
			return -1;
	}
	if (!PyBytes_Check(v) || PyBytes_Size(v) != 1) {
		PyErr_SetString(StructError,
				"char format requires bytes or string of length 1");
		return -1;
	}
	*p = *PyBytes_AsString(v);
	return 0;
}

static int
np_short(char *p, PyObject *v, const formatdef *f)
{
	long x;
	short y;
	if (get_long(v, &x) < 0)
		return -1;
	if (x < SHRT_MIN || x > SHRT_MAX){
		PyErr_SetString(StructError,
				"short format requires " STRINGIFY(SHRT_MIN)
				" <= number <= " STRINGIFY(SHRT_MAX));
		return -1;
	}
	y = (short)x;
	memcpy(p, (char *)&y, sizeof y);
	return 0;
}

static int
np_ushort(char *p, PyObject *v, const formatdef *f)
{
	long x;
	unsigned short y;
	if (get_long(v, &x) < 0)
		return -1;
	if (x < 0 || x > USHRT_MAX){
		PyErr_SetString(StructError,
				"short format requires 0 <= number <= " STRINGIFY(USHRT_MAX));
		return -1;
	}
	y = (unsigned short)x;
	memcpy(p, (char *)&y, sizeof y);
	return 0;
}

static int
np_int(char *p, PyObject *v, const formatdef *f)
{
	long x;
	int y;
	if (get_long(v, &x) < 0)
		return -1;
#if (SIZEOF_LONG > SIZEOF_INT)
	if ((x < ((long)INT_MIN)) || (x > ((long)INT_MAX)))
		return _range_error(f, 0);
#endif
	y = (int)x;
	memcpy(p, (char *)&y, sizeof y);
	return 0;
}

static int
np_uint(char *p, PyObject *v, const formatdef *f)
{
	unsigned long x;
	unsigned int y;
	if (get_ulong(v, &x) < 0)
		return _range_error(f, 1);
	y = (unsigned int)x;
#if (SIZEOF_LONG > SIZEOF_INT)
	if (x > ((unsigned long)UINT_MAX))
		return _range_error(f, 1);
#endif
	memcpy(p, (char *)&y, sizeof y);
	return 0;
}

static int
np_long(char *p, PyObject *v, const formatdef *f)
{
	long x;
	if (get_long(v, &x) < 0)
		return -1;
	memcpy(p, (char *)&x, sizeof x);
	return 0;
}

static int
np_ulong(char *p, PyObject *v, const formatdef *f)
{
	unsigned long x;
	if (get_ulong(v, &x) < 0)
		return _range_error(f, 1);
	memcpy(p, (char *)&x, sizeof x);
	return 0;
}

#ifdef HAVE_LONG_LONG

static int
np_longlong(char *p, PyObject *v, const formatdef *f)
{
	PY_LONG_LONG x;
	if (get_longlong(v, &x) < 0)
		return -1;
	memcpy(p, (char *)&x, sizeof x);
	return 0;
}

static int
np_ulonglong(char *p, PyObject *v, const formatdef *f)
{
	unsigned PY_LONG_LONG x;
	if (get_ulonglong(v, &x) < 0)
		return -1;
	memcpy(p, (char *)&x, sizeof x);
	return 0;
}
#endif


static int
np_bool(char *p, PyObject *v, const formatdef *f)
{
	BOOL_TYPE y; 
	y = PyObject_IsTrue(v);
	memcpy(p, (char *)&y, sizeof y);
	return 0;
}

static int
np_float(char *p, PyObject *v, const formatdef *f)
{
	float x = (float)PyFloat_AsDouble(v);
	if (x == -1 && PyErr_Occurred()) {
		PyErr_SetString(StructError,
				"required argument is not a float");
		return -1;
	}
	memcpy(p, (char *)&x, sizeof x);
	return 0;
}

static int
np_double(char *p, PyObject *v, const formatdef *f)
{
	double x = PyFloat_AsDouble(v);
	if (x == -1 && PyErr_Occurred()) {
		PyErr_SetString(StructError,
				"required argument is not a float");
		return -1;
	}
	memcpy(p, (char *)&x, sizeof(double));
	return 0;
}

static int
np_void_p(char *p, PyObject *v, const formatdef *f)
{
	void *x;

	v = get_pylong(v);
	if (v == NULL)
		return -1;
	assert(PyLong_Check(v));
	x = PyLong_AsVoidPtr(v);
	Py_DECREF(v);
	if (x == NULL && PyErr_Occurred())
		return -1;
	memcpy(p, (char *)&x, sizeof x);
	return 0;
}

static formatdef native_table[] = {
	{'x',	sizeof(char),	0,		NULL},
	{'b',	sizeof(char),	0,		nu_byte,	np_byte},
	{'B',	sizeof(char),	0,		nu_ubyte,	np_ubyte},
	{'c',	sizeof(char),	0,		nu_char,	np_char},
	{'s',	sizeof(char),	0,		NULL},
	{'p',	sizeof(char),	0,		NULL},
	{'h',	sizeof(short),	SHORT_ALIGN,	nu_short,	np_short},
	{'H',	sizeof(short),	SHORT_ALIGN,	nu_ushort,	np_ushort},
	{'i',	sizeof(int),	INT_ALIGN,	nu_int,		np_int},
	{'I',	sizeof(int),	INT_ALIGN,	nu_uint,	np_uint},
	{'l',	sizeof(long),	LONG_ALIGN,	nu_long,	np_long},
	{'L',	sizeof(long),	LONG_ALIGN,	nu_ulong,	np_ulong},
#ifdef HAVE_LONG_LONG
	{'q',	sizeof(PY_LONG_LONG), LONG_LONG_ALIGN, nu_longlong, np_longlong},
	{'Q',	sizeof(PY_LONG_LONG), LONG_LONG_ALIGN, nu_ulonglong,np_ulonglong},
#endif
	{'?',	sizeof(BOOL_TYPE),	BOOL_ALIGN,	nu_bool,	np_bool},
	{'f',	sizeof(float),	FLOAT_ALIGN,	nu_float,	np_float},
	{'d',	sizeof(double),	DOUBLE_ALIGN,	nu_double,	np_double},
	{'P',	sizeof(void *),	VOID_P_ALIGN,	nu_void_p,	np_void_p},
	{0}
};

/* Big-endian routines. *****************************************************/

static PyObject *
bu_int(const char *p, const formatdef *f)
{
	long x = 0;
	Py_ssize_t i = f->size;
	const unsigned char *bytes = (const unsigned char *)p;
	do {
		x = (x<<8) | *bytes++;
	} while (--i > 0);
	/* Extend the sign bit. */
	if (SIZEOF_LONG > f->size)
		x |= -(x & (1L << ((8 * f->size) - 1)));
	return PyLong_FromLong(x);
}

static PyObject *
bu_uint(const char *p, const formatdef *f)
{
	unsigned long x = 0;
	Py_ssize_t i = f->size;
	const unsigned char *bytes = (const unsigned char *)p;
	do {
		x = (x<<8) | *bytes++;
	} while (--i > 0);
	if (x <= LONG_MAX)
		return PyLong_FromLong((long)x);
	return PyLong_FromUnsignedLong(x);
}

static PyObject *
bu_longlong(const char *p, const formatdef *f)
{
#ifdef HAVE_LONG_LONG
	PY_LONG_LONG x = 0;
	Py_ssize_t i = f->size;
	const unsigned char *bytes = (const unsigned char *)p;
	do {
		x = (x<<8) | *bytes++;
	} while (--i > 0);
	/* Extend the sign bit. */
	if (SIZEOF_LONG_LONG > f->size)
		x |= -(x & ((PY_LONG_LONG)1 << ((8 * f->size) - 1)));
	if (x >= LONG_MIN && x <= LONG_MAX)
		return PyLong_FromLong(Py_SAFE_DOWNCAST(x, PY_LONG_LONG, long));
	return PyLong_FromLongLong(x);
#else
	return _PyLong_FromByteArray((const unsigned char *)p,
				      8,
				      0, /* little-endian */
				      1  /* signed */);
#endif
}

static PyObject *
bu_ulonglong(const char *p, const formatdef *f)
{
#ifdef HAVE_LONG_LONG
	unsigned PY_LONG_LONG x = 0;
	Py_ssize_t i = f->size;
	const unsigned char *bytes = (const unsigned char *)p;
	do {
		x = (x<<8) | *bytes++;
	} while (--i > 0);
	if (x <= LONG_MAX)
		return PyLong_FromLong(Py_SAFE_DOWNCAST(x, unsigned PY_LONG_LONG, long));
	return PyLong_FromUnsignedLongLong(x);
#else
	return _PyLong_FromByteArray((const unsigned char *)p,
				      8,
				      0, /* little-endian */
				      0  /* signed */);
#endif
}

static PyObject *
bu_float(const char *p, const formatdef *f)
{
	return unpack_float(p, 0);
}

static PyObject *
bu_double(const char *p, const formatdef *f)
{
	return unpack_double(p, 0);
}

static PyObject *
bu_bool(const char *p, const formatdef *f)
{
	char x;
	memcpy((char *)&x, p, sizeof x);
	return PyBool_FromLong(x != 0);
}

static int
bp_int(char *p, PyObject *v, const formatdef *f)
{
	long x;
	Py_ssize_t i;
	if (get_wrapped_long(v, &x) < 0)
		return -1;
	i = f->size;
	if (i != SIZEOF_LONG) {
		if ((i == 2) && (x < -32768 || x > 32767))
			RANGE_ERROR(x, f, 0, 0xffffL);
#if (SIZEOF_LONG != 4)
		else if ((i == 4) && (x < -2147483648L || x > 2147483647L))
			RANGE_ERROR(x, f, 0, 0xffffffffL);
#endif
#ifdef PY_STRUCT_OVERFLOW_MASKING
		else if ((i == 1) && (x < -128 || x > 127))
			RANGE_ERROR(x, f, 0, 0xffL);
#endif
	}
	do {
		p[--i] = (char)x;
		x >>= 8;
	} while (i > 0);
	return 0;
}

static int
bp_uint(char *p, PyObject *v, const formatdef *f)
{
	unsigned long x;
	Py_ssize_t i;
	if (get_wrapped_ulong(v, &x) < 0)
		return -1;
	i = f->size;
	if (i != SIZEOF_LONG) {
		unsigned long maxint = 1;
		maxint <<= (unsigned long)(i * 8);
		if (x >= maxint)
			RANGE_ERROR(x, f, 1, maxint - 1);
	}
	do {
		p[--i] = (char)x;
		x >>= 8;
	} while (i > 0);
	return 0;
}

static int
bp_longlong(char *p, PyObject *v, const formatdef *f)
{
	int res;
	v = get_pylong(v);
	if (v == NULL)
		return -1;
	res = _PyLong_AsByteArray((PyLongObject *)v,
			   	  (unsigned char *)p,
				  8,
				  0, /* little_endian */
				  1  /* signed */);
	Py_DECREF(v);
	return res;
}

static int
bp_ulonglong(char *p, PyObject *v, const formatdef *f)
{
	int res;
	v = get_pylong(v);
	if (v == NULL)
		return -1;
	res = _PyLong_AsByteArray((PyLongObject *)v,
			   	  (unsigned char *)p,
				  8,
				  0, /* little_endian */
				  0  /* signed */);
	Py_DECREF(v);
	return res;
}

static int
bp_float(char *p, PyObject *v, const formatdef *f)
{
	double x = PyFloat_AsDouble(v);
	if (x == -1 && PyErr_Occurred()) {
		PyErr_SetString(StructError,
				"required argument is not a float");
		return -1;
	}
	return _PyFloat_Pack4(x, (unsigned char *)p, 0);
}

static int
bp_double(char *p, PyObject *v, const formatdef *f)
{
	double x = PyFloat_AsDouble(v);
	if (x == -1 && PyErr_Occurred()) {
		PyErr_SetString(StructError,
				"required argument is not a float");
		return -1;
	}
	return _PyFloat_Pack8(x, (unsigned char *)p, 0);
}

static int
bp_bool(char *p, PyObject *v, const formatdef *f)
{
	char y; 
	y = PyObject_IsTrue(v);
	memcpy(p, (char *)&y, sizeof y);
	return 0;
}

static formatdef bigendian_table[] = {
	{'x',	1,		0,		NULL},
#ifdef PY_STRUCT_OVERFLOW_MASKING
	/* Native packers do range checking without overflow masking. */
	{'b',	1,		0,		nu_byte,	bp_int},
	{'B',	1,		0,		nu_ubyte,	bp_uint},
#else
	{'b',	1,		0,		nu_byte,	np_byte},
	{'B',	1,		0,		nu_ubyte,	np_ubyte},
#endif
	{'c',	1,		0,		nu_char,	np_char},
	{'s',	1,		0,		NULL},
	{'p',	1,		0,		NULL},
	{'h',	2,		0,		bu_int,		bp_int},
	{'H',	2,		0,		bu_uint,	bp_uint},
	{'i',	4,		0,		bu_int,		bp_int},
	{'I',	4,		0,		bu_uint,	bp_uint},
	{'l',	4,		0,		bu_int,		bp_int},
	{'L',	4,		0,		bu_uint,	bp_uint},
	{'q',	8,		0,		bu_longlong,	bp_longlong},
	{'Q',	8,		0,		bu_ulonglong,	bp_ulonglong},
	{'?',	1,		0,		bu_bool,	bp_bool},
	{'f',	4,		0,		bu_float,	bp_float},
	{'d',	8,		0,		bu_double,	bp_double},
	{0}
};

/* Little-endian routines. *****************************************************/

static PyObject *
lu_int(const char *p, const formatdef *f)
{
	long x = 0;
	Py_ssize_t i = f->size;
	const unsigned char *bytes = (const unsigned char *)p;
	do {
		x = (x<<8) | bytes[--i];
	} while (i > 0);
	/* Extend the sign bit. */
	if (SIZEOF_LONG > f->size)
		x |= -(x & (1L << ((8 * f->size) - 1)));
	return PyLong_FromLong(x);
}

static PyObject *
lu_uint(const char *p, const formatdef *f)
{
	unsigned long x = 0;
	Py_ssize_t i = f->size;
	const unsigned char *bytes = (const unsigned char *)p;
	do {
		x = (x<<8) | bytes[--i];
	} while (i > 0);
	if (x <= LONG_MAX)
		return PyLong_FromLong((long)x);
	return PyLong_FromUnsignedLong((long)x);
}

static PyObject *
lu_longlong(const char *p, const formatdef *f)
{
#ifdef HAVE_LONG_LONG
	PY_LONG_LONG x = 0;
	Py_ssize_t i = f->size;
	const unsigned char *bytes = (const unsigned char *)p;
	do {
		x = (x<<8) | bytes[--i];
	} while (i > 0);
	/* Extend the sign bit. */
	if (SIZEOF_LONG_LONG > f->size)
		x |= -(x & ((PY_LONG_LONG)1 << ((8 * f->size) - 1)));
	if (x >= LONG_MIN && x <= LONG_MAX)
		return PyLong_FromLong(Py_SAFE_DOWNCAST(x, PY_LONG_LONG, long));
	return PyLong_FromLongLong(x);
#else
	return _PyLong_FromByteArray((const unsigned char *)p,
				      8,
				      1, /* little-endian */
				      1  /* signed */);
#endif
}

static PyObject *
lu_ulonglong(const char *p, const formatdef *f)
{
#ifdef HAVE_LONG_LONG
	unsigned PY_LONG_LONG x = 0;
	Py_ssize_t i = f->size;
	const unsigned char *bytes = (const unsigned char *)p;
	do {
		x = (x<<8) | bytes[--i];
	} while (i > 0);
	if (x <= LONG_MAX)
		return PyLong_FromLong(Py_SAFE_DOWNCAST(x, unsigned PY_LONG_LONG, long));
	return PyLong_FromUnsignedLongLong(x);
#else
	return _PyLong_FromByteArray((const unsigned char *)p,
				      8,
				      1, /* little-endian */
				      0  /* signed */);
#endif
}

static PyObject *
lu_float(const char *p, const formatdef *f)
{
	return unpack_float(p, 1);
}

static PyObject *
lu_double(const char *p, const formatdef *f)
{
	return unpack_double(p, 1);
}

static int
lp_int(char *p, PyObject *v, const formatdef *f)
{
	long x;
	Py_ssize_t i;
	if (get_wrapped_long(v, &x) < 0)
		return -1;
	i = f->size;
	if (i != SIZEOF_LONG) {
		if ((i == 2) && (x < -32768 || x > 32767))
			RANGE_ERROR(x, f, 0, 0xffffL);
#if (SIZEOF_LONG != 4)
		else if ((i == 4) && (x < -2147483648L || x > 2147483647L))
			RANGE_ERROR(x, f, 0, 0xffffffffL);
#endif
#ifdef PY_STRUCT_OVERFLOW_MASKING
		else if ((i == 1) && (x < -128 || x > 127))
			RANGE_ERROR(x, f, 0, 0xffL);
#endif
	}
	do {
		*p++ = (char)x;
		x >>= 8;
	} while (--i > 0);
	return 0;
}

static int
lp_uint(char *p, PyObject *v, const formatdef *f)
{
	unsigned long x;
	Py_ssize_t i;
	if (get_wrapped_ulong(v, &x) < 0)
		return -1;
	i = f->size;
	if (i != SIZEOF_LONG) {
		unsigned long maxint = 1;
		maxint <<= (unsigned long)(i * 8);
		if (x >= maxint)
			RANGE_ERROR(x, f, 1, maxint - 1);
	}
	do {
		*p++ = (char)x;
		x >>= 8;
	} while (--i > 0);
	return 0;
}

static int
lp_longlong(char *p, PyObject *v, const formatdef *f)
{
	int res;
	v = get_pylong(v);
	if (v == NULL)
		return -1;
	res = _PyLong_AsByteArray((PyLongObject*)v,
			   	  (unsigned char *)p,
				  8,
				  1, /* little_endian */
				  1  /* signed */);
	Py_DECREF(v);
	return res;
}

static int
lp_ulonglong(char *p, PyObject *v, const formatdef *f)
{
	int res;
	v = get_pylong(v);
	if (v == NULL)
		return -1;
	res = _PyLong_AsByteArray((PyLongObject*)v,
			   	  (unsigned char *)p,
				  8,
				  1, /* little_endian */
				  0  /* signed */);
	Py_DECREF(v);
	return res;
}

static int
lp_float(char *p, PyObject *v, const formatdef *f)
{
	double x = PyFloat_AsDouble(v);
	if (x == -1 && PyErr_Occurred()) {
		PyErr_SetString(StructError,
				"required argument is not a float");
		return -1;
	}
	return _PyFloat_Pack4(x, (unsigned char *)p, 1);
}

static int
lp_double(char *p, PyObject *v, const formatdef *f)
{
	double x = PyFloat_AsDouble(v);
	if (x == -1 && PyErr_Occurred()) {
		PyErr_SetString(StructError,
				"required argument is not a float");
		return -1;
	}
	return _PyFloat_Pack8(x, (unsigned char *)p, 1);
}

static formatdef lilendian_table[] = {
	{'x',	1,		0,		NULL},
#ifdef PY_STRUCT_OVERFLOW_MASKING
	/* Native packers do range checking without overflow masking. */
	{'b',	1,		0,		nu_byte,	lp_int},
	{'B',	1,		0,		nu_ubyte,	lp_uint},
#else
	{'b',	1,		0,		nu_byte,	np_byte},
	{'B',	1,		0,		nu_ubyte,	np_ubyte},
#endif
	{'c',	1,		0,		nu_char,	np_char},
	{'s',	1,		0,		NULL},
	{'p',	1,		0,		NULL},
	{'h',	2,		0,		lu_int,		lp_int},
	{'H',	2,		0,		lu_uint,	lp_uint},
	{'i',	4,		0,		lu_int,		lp_int},
	{'I',	4,		0,		lu_uint,	lp_uint},
	{'l',	4,		0,		lu_int,		lp_int},
	{'L',	4,		0,		lu_uint,	lp_uint},
	{'q',	8,		0,		lu_longlong,	lp_longlong},
	{'Q',	8,		0,		lu_ulonglong,	lp_ulonglong},
	{'?',	1,		0,		bu_bool,	bp_bool}, /* Std rep not endian dep,
		but potentially different from native rep -- reuse bx_bool funcs. */
	{'f',	4,		0,		lu_float,	lp_float},
	{'d',	8,		0,		lu_double,	lp_double},
	{0}
};


static const formatdef *
whichtable(char **pfmt)
{
	const char *fmt = (*pfmt)++; /* May be backed out of later */
	switch (*fmt) {
	case '<':
		return lilendian_table;
	case '>':
	case '!': /* Network byte order is big-endian */
		return bigendian_table;
	case '=': { /* Host byte order -- different from native in aligment! */
		int n = 1;
		char *p = (char *) &n;
		if (*p == 1)
			return lilendian_table;
		else
			return bigendian_table;
	}
	default:
		--*pfmt; /* Back out of pointer increment */
		/* Fall through */
	case '@':
		return native_table;
	}
}


/* Get the table entry for a format code */

static const formatdef *
getentry(int c, const formatdef *f)
{
	for (; f->format != '\0'; f++) {
		if (f->format == c) {
			return f;
		}
	}
	PyErr_SetString(StructError, "bad char in struct format");
	return NULL;
}


/* Align a size according to a format code */

static int
align(Py_ssize_t size, char c, const formatdef *e)
{
	if (e->format == c) {
		if (e->alignment) {
			size = ((size + e->alignment - 1)
				/ e->alignment)
				* e->alignment;
		}
	}
	return size;
}


/* calculate the size of a format string */

static int
prepare_s(PyStructObject *self)
{
	const formatdef *f;
	const formatdef *e;
	formatcode *codes;

	const char *s;
	const char *fmt;
	char c;
	Py_ssize_t size, len, num, itemsize, x;

	fmt = PyBytes_AS_STRING(self->s_format);

	f = whichtable((char **)&fmt);

	s = fmt;
	size = 0;
	len = 0;
	while ((c = *s++) != '\0') {
		if (isspace(Py_CHARMASK(c)))
			continue;
		if ('0' <= c && c <= '9') {
			num = c - '0';
			while ('0' <= (c = *s++) && c <= '9') {
				x = num*10 + (c - '0');
				if (x/10 != num) {
					PyErr_SetString(
						StructError,
						"overflow in item count");
					return -1;
				}
				num = x;
			}
			if (c == '\0')
				break;
		}
		else
			num = 1;

		e = getentry(c, f);
		if (e == NULL)
			return -1;

		switch (c) {
			case 's': /* fall through */
			case 'p': len++; break;
			case 'x': break;
			default: len += num; break;
		}

		itemsize = e->size;
		size = align(size, c, e);
		x = num * itemsize;
		size += x;
		if (x/itemsize != num || size < 0) {
			PyErr_SetString(StructError,
					"total struct size too long");
			return -1;
		}
	}

	/* check for overflow */
	if ((len + 1) > (PY_SSIZE_T_MAX / sizeof(formatcode))) {
		PyErr_NoMemory();
		return -1;
	}

	self->s_size = size;
	self->s_len = len;
	codes = PyMem_MALLOC((len + 1) * sizeof(formatcode));
	if (codes == NULL) {
		PyErr_NoMemory();
		return -1;
	}
	self->s_codes = codes;

	s = fmt;
	size = 0;
	while ((c = *s++) != '\0') {
		if (isspace(Py_CHARMASK(c)))
			continue;
		if ('0' <= c && c <= '9') {
			num = c - '0';
			while ('0' <= (c = *s++) && c <= '9')
				num = num*10 + (c - '0');
			if (c == '\0')
				break;
		}
		else
			num = 1;

		e = getentry(c, f);

		size = align(size, c, e);
		if (c == 's' || c == 'p') {
			codes->offset = size;
			codes->size = num;
			codes->fmtdef = e;
			codes++;
			size += num;
		} else if (c == 'x') {
			size += num;
		} else {
			while (--num >= 0) {
				codes->offset = size;
				codes->size = e->size;
				codes->fmtdef = e;
				codes++;
				size += e->size;
			}
		}
	}
	codes->fmtdef = NULL;
	codes->offset = size;
	codes->size = 0;

	return 0;
}

static PyObject *
s_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
{
	PyObject *self;

	assert(type != NULL && type->tp_alloc != NULL);

	self = type->tp_alloc(type, 0);
	if (self != NULL) {
		PyStructObject *s = (PyStructObject*)self;
		Py_INCREF(Py_None);
		s->s_format = Py_None;
		s->s_codes = NULL;
		s->s_size = -1;
		s->s_len = -1;
	}
	return self;
}

static int
s_init(PyObject *self, PyObject *args, PyObject *kwds)
{
	PyStructObject *soself = (PyStructObject *)self;
	PyObject *o_format = NULL;
	int ret = 0;
	static char *kwlist[] = {"format", 0};

	assert(PyStruct_Check(self));

	if (!PyArg_ParseTupleAndKeywords(args, kwds, "O:Struct", kwlist,
					 &o_format))
		return -1;

	if (PyUnicode_Check(o_format)) {
		o_format = PyUnicode_AsASCIIString(o_format);
		if (o_format == NULL)
			return -1;
	}
	/* XXX support buffer interface, too */
	else {
		Py_INCREF(o_format);
	}

	if (!PyBytes_Check(o_format)) {
		Py_DECREF(o_format);
		PyErr_Format(PyExc_TypeError,
			     "Struct() argument 1 must be bytes, not %.200s",
			     Py_TYPE(o_format)->tp_name);
		return -1;
	}

	Py_CLEAR(soself->s_format);
	soself->s_format = o_format;

	ret = prepare_s(soself);
	return ret;
}

static void
s_dealloc(PyStructObject *s)
{
	if (s->weakreflist != NULL)
		PyObject_ClearWeakRefs((PyObject *)s);
	if (s->s_codes != NULL) {
		PyMem_FREE(s->s_codes);
	}
	Py_XDECREF(s->s_format);
	Py_TYPE(s)->tp_free((PyObject *)s);
}

static PyObject *
s_unpack_internal(PyStructObject *soself, char *startfrom) {
	formatcode *code;
	Py_ssize_t i = 0;
	PyObject *result = PyTuple_New(soself->s_len);
	if (result == NULL)
		return NULL;

	for (code = soself->s_codes; code->fmtdef != NULL; code++) {
		PyObject *v;
		const formatdef *e = code->fmtdef;
		const char *res = startfrom + code->offset;
		if (e->format == 's') {
			v = PyBytes_FromStringAndSize(res, code->size);
		} else if (e->format == 'p') {
			Py_ssize_t n = *(unsigned char*)res;
			if (n >= code->size)
				n = code->size - 1;
			v = PyBytes_FromStringAndSize(res + 1, n);
		} else {
			v = e->unpack(res, e);
		}
		if (v == NULL)
			goto fail;
		PyTuple_SET_ITEM(result, i++, v);
	}

	return result;
fail:
	Py_DECREF(result);
	return NULL;
}


PyDoc_STRVAR(s_unpack__doc__,
"S.unpack(buffer) -> (v1, v2, ...)\n\
\n\
Return tuple containing values unpacked according to this Struct's format.\n\
Requires len(buffer) == self.size. See struct.__doc__ for more on format\n\
strings.");

static PyObject *
s_unpack(PyObject *self, PyObject *input)
{
	Py_buffer vbuf;
	PyObject *result;
	PyStructObject *soself = (PyStructObject *)self;

	assert(PyStruct_Check(self));
	assert(soself->s_codes != NULL);
	if (PyObject_GetBuffer(input, &vbuf, PyBUF_SIMPLE) < 0)
		return NULL;
	if (vbuf.len != soself->s_size) {
		PyErr_Format(StructError,
			     "unpack requires a bytes argument of length %zd",
			     soself->s_size);
                PyObject_ReleaseBuffer(input, &vbuf);
		return NULL;
	}
	result = s_unpack_internal(soself, vbuf.buf);
	PyObject_ReleaseBuffer(input, &vbuf);
	return result;
}

PyDoc_STRVAR(s_unpack_from__doc__,
"S.unpack_from(buffer[, offset]) -> (v1, v2, ...)\n\
\n\
Return tuple containing values unpacked according to this Struct's format.\n\
Unlike unpack, unpack_from can unpack values from any object supporting\n\
the buffer API, not just str. Requires len(buffer[offset:]) >= self.size.\n\
See struct.__doc__ for more on format strings.");

static PyObject *
s_unpack_from(PyObject *self, PyObject *args, PyObject *kwds)
{
	static char *kwlist[] = {"buffer", "offset", 0};

	PyObject *input;
	Py_ssize_t offset = 0;
	Py_buffer vbuf;
	PyObject *result;
	PyStructObject *soself = (PyStructObject *)self;

	assert(PyStruct_Check(self));
	assert(soself->s_codes != NULL);

	if (!PyArg_ParseTupleAndKeywords(args, kwds,
					 "O|n:unpack_from", kwlist,
					 &input, &offset))
		return NULL;
	if (PyObject_GetBuffer(input, &vbuf, PyBUF_SIMPLE) < 0)
		return NULL;
	if (offset < 0)
		offset += vbuf.len;
	if (offset < 0 || vbuf.len - offset < soself->s_size) {
		PyErr_Format(StructError,
			"unpack_from requires a buffer of at least %zd bytes",
			soself->s_size);
                PyObject_ReleaseBuffer(input, &vbuf);
		return NULL;
	}
	result = s_unpack_internal(soself, (char*)vbuf.buf + offset);
	PyObject_ReleaseBuffer(input, &vbuf);
	return result;
}


/*
 * Guts of the pack function.
 *
 * Takes a struct object, a tuple of arguments, and offset in that tuple of
 * argument for where to start processing the arguments for packing, and a
 * character buffer for writing the packed string.  The caller must insure
 * that the buffer may contain the required length for packing the arguments.
 * 0 is returned on success, 1 is returned if there is an error.
 *
 */
static int
s_pack_internal(PyStructObject *soself, PyObject *args, int offset, char* buf)
{
	formatcode *code;
	/* XXX(nnorwitz): why does i need to be a local?  can we use
	   the offset parameter or do we need the wider width? */
	Py_ssize_t i;

	memset(buf, '\0', soself->s_size);
	i = offset;
	for (code = soself->s_codes; code->fmtdef != NULL; code++) {
		Py_ssize_t n;
		PyObject *v = PyTuple_GET_ITEM(args, i++);
		const formatdef *e = code->fmtdef;
		char *res = buf + code->offset;
		if (e->format == 's') {
			int isstring;
			void *p;
			if (PyUnicode_Check(v)) {
				v = _PyUnicode_AsDefaultEncodedString(v, NULL);
				if (v == NULL)
					return -1;
			}
			isstring = PyBytes_Check(v);
			if (!isstring && !PyByteArray_Check(v)) {
				PyErr_SetString(StructError,
						"argument for 's' must be a bytes or string");
				return -1;
			}
			if (isstring) {
				n = PyBytes_GET_SIZE(v);
				p = PyBytes_AS_STRING(v);
			}
			else {
				n = PyByteArray_GET_SIZE(v);
				p = PyByteArray_AS_STRING(v);
			}
			if (n > code->size)
				n = code->size;
			if (n > 0)
				memcpy(res, p, n);
		} else if (e->format == 'p') {
			int isstring;
			void *p;
			if (PyUnicode_Check(v)) {
				v = _PyUnicode_AsDefaultEncodedString(v, NULL);
				if (v == NULL)
					return -1;
			}
			isstring = PyBytes_Check(v);
			if (!isstring && !PyByteArray_Check(v)) {
				PyErr_SetString(StructError,
						"argument for 'p' must be a bytes or string");
				return -1;
			}
			if (isstring) {
				n = PyBytes_GET_SIZE(v);
				p = PyBytes_AS_STRING(v);
			}
			else {
				n = PyByteArray_GET_SIZE(v);
				p = PyByteArray_AS_STRING(v);
			}
			if (n > (code->size - 1))
				n = code->size - 1;
			if (n > 0)
				memcpy(res + 1, p, n);
			if (n > 255)
				n = 255;
			*res = Py_SAFE_DOWNCAST(n, Py_ssize_t, unsigned char);
		} else {
			if (e->pack(res, v, e) < 0) {
				if (PyLong_Check(v) && PyErr_ExceptionMatches(PyExc_OverflowError))
					PyErr_SetString(StructError,
							"long too large to convert to int");
				return -1;
			}
		}
	}

	/* Success */
	return 0;
}


PyDoc_STRVAR(s_pack__doc__,
"S.pack(v1, v2, ...) -> bytes\n\
\n\
Return a bytes containing values v1, v2, ... packed according to this\n\
Struct's format. See struct.__doc__ for more on format strings.");

static PyObject *
s_pack(PyObject *self, PyObject *args)
{
	PyStructObject *soself;
	PyObject *result;

	/* Validate arguments. */
	soself = (PyStructObject *)self;
	assert(PyStruct_Check(self));
	assert(soself->s_codes != NULL);
	if (PyTuple_GET_SIZE(args) != soself->s_len)
	{
		PyErr_Format(StructError,
			"pack requires exactly %zd arguments", soself->s_len);
		return NULL;
	}

	/* Allocate a new string */
	result = PyBytes_FromStringAndSize((char *)NULL, soself->s_size);
	if (result == NULL)
		return NULL;

	/* Call the guts */
	if ( s_pack_internal(soself, args, 0, PyBytes_AS_STRING(result)) != 0 ) {
		Py_DECREF(result);
		return NULL;
	}

	return result;
}

PyDoc_STRVAR(s_pack_into__doc__,
"S.pack_into(buffer, offset, v1, v2, ...)\n\
\n\
Pack the values v1, v2, ... according to this Struct's format, write \n\
the packed bytes into the writable buffer buf starting at offset.  Note\n\
that the offset is not an optional argument.  See struct.__doc__ for \n\
more on format strings.");

static PyObject *
s_pack_into(PyObject *self, PyObject *args)
{
	PyStructObject *soself;
	char *buffer;
	Py_ssize_t buffer_len, offset;

	/* Validate arguments.  +1 is for the first arg as buffer. */
	soself = (PyStructObject *)self;
	assert(PyStruct_Check(self));
	assert(soself->s_codes != NULL);
	if (PyTuple_GET_SIZE(args) != (soself->s_len + 2))
	{
		PyErr_Format(StructError,
			     "pack_into requires exactly %zd arguments",
			     (soself->s_len + 2));
		return NULL;
	}

	/* Extract a writable memory buffer from the first argument */
	if ( PyObject_AsWriteBuffer(PyTuple_GET_ITEM(args, 0),
								(void**)&buffer, &buffer_len) == -1 ) {
		return NULL;
	}
	assert( buffer_len >= 0 );

	/* Extract the offset from the first argument */
	offset = PyLong_AsSsize_t(PyTuple_GET_ITEM(args, 1));

	/* Support negative offsets. */
	if (offset < 0)
		offset += buffer_len;

	/* Check boundaries */
	if (offset < 0 || (buffer_len - offset) < soself->s_size) {
		PyErr_Format(StructError,
			     "pack_into requires a buffer of at least %zd bytes",
			     soself->s_size);
		return NULL;
	}

	/* Call the guts */
	if ( s_pack_internal(soself, args, 2, buffer + offset) != 0 ) {
		return NULL;
	}

	Py_RETURN_NONE;
}

static PyObject *
s_get_format(PyStructObject *self, void *unused)
{
	Py_INCREF(self->s_format);
	return self->s_format;
}

static PyObject *
s_get_size(PyStructObject *self, void *unused)
{
    return PyLong_FromSsize_t(self->s_size);
}

/* List of functions */

static struct PyMethodDef s_methods[] = {
	{"pack",	s_pack,		METH_VARARGS, s_pack__doc__},
	{"pack_into",	s_pack_into,	METH_VARARGS, s_pack_into__doc__},
	{"unpack",	s_unpack,       METH_O, s_unpack__doc__},
	{"unpack_from",	(PyCFunction)s_unpack_from, METH_VARARGS|METH_KEYWORDS,
			s_unpack_from__doc__},
	{NULL,	 NULL}		/* sentinel */
};

PyDoc_STRVAR(s__doc__, "Compiled struct object");

#define OFF(x) offsetof(PyStructObject, x)

static PyGetSetDef s_getsetlist[] = {
	{"format", (getter)s_get_format, (setter)NULL, "struct format string", NULL},
	{"size", (getter)s_get_size, (setter)NULL, "struct size in bytes", NULL},
	{NULL} /* sentinel */
};

static
PyTypeObject PyStructType = {
	PyVarObject_HEAD_INIT(NULL, 0)
	"Struct",
	sizeof(PyStructObject),
	0,
	(destructor)s_dealloc,	/* tp_dealloc */
	0,					/* tp_print */
	0,					/* tp_getattr */
	0,					/* tp_setattr */
	0,					/* tp_compare */
	0,					/* tp_repr */
	0,					/* tp_as_number */
	0,					/* tp_as_sequence */
	0,					/* tp_as_mapping */
	0,					/* tp_hash */
	0,					/* tp_call */
	0,					/* tp_str */
	PyObject_GenericGetAttr,	/* tp_getattro */
	PyObject_GenericSetAttr,	/* tp_setattro */
	0,					/* tp_as_buffer */
	Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
	s__doc__,			/* tp_doc */
	0,					/* tp_traverse */
	0,					/* tp_clear */
	0,					/* tp_richcompare */
	offsetof(PyStructObject, weakreflist),	/* tp_weaklistoffset */
	0,					/* tp_iter */
	0,					/* tp_iternext */
	s_methods,			/* tp_methods */
	NULL,				/* tp_members */
	s_getsetlist,		/* tp_getset */
	0,					/* tp_base */
	0,					/* tp_dict */
	0,					/* tp_descr_get */
	0,					/* tp_descr_set */
	0,					/* tp_dictoffset */
	s_init,				/* tp_init */
	PyType_GenericAlloc,/* tp_alloc */
	s_new,				/* tp_new */
	PyObject_Del,		/* tp_free */
};


/* ---- Standalone functions  ---- */

#define MAXCACHE 100
static PyObject *cache = NULL;

static PyObject *
cache_struct(PyObject *fmt)
{
	PyObject * s_object;

	if (cache == NULL) {
		cache = PyDict_New();
		if (cache == NULL)
			return NULL;
	}

	s_object = PyDict_GetItem(cache, fmt);
	if (s_object != NULL) {
		Py_INCREF(s_object);
		return s_object;
	}

	s_object = PyObject_CallFunctionObjArgs((PyObject *)(&PyStructType), fmt, NULL);
	if (s_object != NULL) {
		if (PyDict_Size(cache) >= MAXCACHE)
			PyDict_Clear(cache);
		/* Attempt to cache the result */
		if (PyDict_SetItem(cache, fmt, s_object) == -1)
			PyErr_Clear();
	}
	return s_object;
}

PyDoc_STRVAR(clearcache_doc,
"Clear the internal cache.");

static PyObject *
clearcache(PyObject *self)
{
	Py_CLEAR(cache);
	Py_RETURN_NONE;
}

PyDoc_STRVAR(calcsize_doc,
"Return size of C struct described by format string fmt.");

static PyObject *
calcsize(PyObject *self, PyObject *fmt)
{
	Py_ssize_t n;
	PyObject *s_object = cache_struct(fmt);
	if (s_object == NULL)
		return NULL;
	n = ((PyStructObject *)s_object)->s_size;
	Py_DECREF(s_object);
    	return PyLong_FromSsize_t(n);
}

PyDoc_STRVAR(pack_doc,
"Return bytes containing values v1, v2, ... packed according to fmt.");

static PyObject *
pack(PyObject *self, PyObject *args)
{
	PyObject *s_object, *fmt, *newargs, *result;
	Py_ssize_t n = PyTuple_GET_SIZE(args);

	if (n == 0) {
		PyErr_SetString(PyExc_TypeError, "missing format argument");
		return NULL;
	}
	fmt = PyTuple_GET_ITEM(args, 0);
	newargs = PyTuple_GetSlice(args, 1, n);
	if (newargs == NULL)
		return NULL;

	s_object = cache_struct(fmt);
	if (s_object == NULL) {
		Py_DECREF(newargs);
		return NULL;
	}
    	result = s_pack(s_object, newargs);
	Py_DECREF(newargs);
	Py_DECREF(s_object);
	return result;
}

PyDoc_STRVAR(pack_into_doc,
"Pack the values v1, v2, ... according to fmt.\n\
Write the packed bytes into the writable buffer buf starting at offset.");

static PyObject *
pack_into(PyObject *self, PyObject *args)
{
	PyObject *s_object, *fmt, *newargs, *result;
	Py_ssize_t n = PyTuple_GET_SIZE(args);

	if (n == 0) {
		PyErr_SetString(PyExc_TypeError, "missing format argument");
		return NULL;
	}
	fmt = PyTuple_GET_ITEM(args, 0);
	newargs = PyTuple_GetSlice(args, 1, n);
	if (newargs == NULL)
		return NULL;

	s_object = cache_struct(fmt);
	if (s_object == NULL) {
		Py_DECREF(newargs);
		return NULL;
	}
    	result = s_pack_into(s_object, newargs);
	Py_DECREF(newargs);
	Py_DECREF(s_object);
	return result;
}

PyDoc_STRVAR(unpack_doc,
"Unpack the bytes containing packed C structure data, according to fmt.\n\
Requires len(bytes) == calcsize(fmt).");

static PyObject *
unpack(PyObject *self, PyObject *args)
{
	PyObject *s_object, *fmt, *inputstr, *result;

	if (!PyArg_UnpackTuple(args, "unpack", 2, 2, &fmt, &inputstr))
		return NULL;

	s_object = cache_struct(fmt);
	if (s_object == NULL)
		return NULL;
    	result = s_unpack(s_object, inputstr);
	Py_DECREF(s_object);
	return result;
}

PyDoc_STRVAR(unpack_from_doc,
"Unpack the buffer, containing packed C structure data, according to\n\
fmt, starting at offset. Requires len(buffer[offset:]) >= calcsize(fmt).");

static PyObject *
unpack_from(PyObject *self, PyObject *args, PyObject *kwds)
{
	PyObject *s_object, *fmt, *newargs, *result;
	Py_ssize_t n = PyTuple_GET_SIZE(args);

	if (n == 0) {
		PyErr_SetString(PyExc_TypeError, "missing format argument");
		return NULL;
	}
	fmt = PyTuple_GET_ITEM(args, 0);
	newargs = PyTuple_GetSlice(args, 1, n);
	if (newargs == NULL)
		return NULL;

	s_object = cache_struct(fmt);
	if (s_object == NULL) {
		Py_DECREF(newargs);
		return NULL;
	}
    	result = s_unpack_from(s_object, newargs, kwds);
	Py_DECREF(newargs);
	Py_DECREF(s_object);
	return result;
}

static struct PyMethodDef module_functions[] = {
	{"_clearcache",	(PyCFunction)clearcache,	METH_NOARGS, 	clearcache_doc},
	{"calcsize",	calcsize,	METH_O, 	calcsize_doc},
	{"pack",	pack,		METH_VARARGS, 	pack_doc},
	{"pack_into",	pack_into,	METH_VARARGS, 	pack_into_doc},
	{"unpack",	unpack,       	METH_VARARGS, 	unpack_doc},
	{"unpack_from",	(PyCFunction)unpack_from, 	
			METH_VARARGS|METH_KEYWORDS, 	unpack_from_doc},
	{NULL,	 NULL}		/* sentinel */
};


/* Module initialization */

PyDoc_STRVAR(module_doc,
"Functions to convert between Python values and C structs.\n\
Python bytes objects are used to hold the data representing the C struct\n\
and also as format strings to describe the layout of data in the C struct.\n\
\n\
The optional first format char indicates byte order, size and alignment:\n\
 @: native order, size & alignment (default)\n\
 =: native order, std. size & alignment\n\
 <: little-endian, std. size & alignment\n\
 >: big-endian, std. size & alignment\n\
 !: same as >\n\
\n\
The remaining chars indicate types of args and must match exactly;\n\
these can be preceded by a decimal repeat count:\n\
  x: pad byte (no data); c:char; b:signed byte; B:unsigned byte;\n\
  h:short; H:unsigned short; i:int; I:unsigned int;\n\
  l:long; L:unsigned long; f:float; d:double.\n\
Special cases (preceding decimal count indicates length):\n\
  s:string (array of char); p: pascal string (with count byte).\n\
Special case (only available in native format):\n\
  P:an integer type that is wide enough to hold a pointer.\n\
Special case (not in native mode unless 'long long' in platform C):\n\
  q:long long; Q:unsigned long long\n\
Whitespace between formats is ignored.\n\
\n\
The variable struct.error is an exception raised on errors.\n");


static struct PyModuleDef _structmodule = {
	PyModuleDef_HEAD_INIT,
	"_struct",
	module_doc,
	-1,
	module_functions,
	NULL,
	NULL,
	NULL,
	NULL
};

PyMODINIT_FUNC
PyInit__struct(void)
{
	PyObject *ver, *m;

	ver = PyBytes_FromString("0.2");
	if (ver == NULL)
		return NULL;

	m = PyModule_Create(&_structmodule);
	if (m == NULL)
		return NULL;

	Py_TYPE(&PyStructType) = &PyType_Type;
	if (PyType_Ready(&PyStructType) < 0)
		return NULL;

#ifdef PY_STRUCT_OVERFLOW_MASKING
	if (pyint_zero == NULL) {
		pyint_zero = PyLong_FromLong(0);
		if (pyint_zero == NULL)
			return NULL;
	}
	if (pylong_ulong_mask == NULL) {
#if (SIZEOF_LONG == 4)
		pylong_ulong_mask = PyLong_FromString("FFFFFFFF", NULL, 16);
#else
		pylong_ulong_mask = PyLong_FromString("FFFFFFFFFFFFFFFF", NULL, 16);
#endif
		if (pylong_ulong_mask == NULL)
			return NULL;
	}

#else
	/* This speed trick can't be used until overflow masking goes away, because
	   native endian always raises exceptions instead of overflow masking. */

	/* Check endian and swap in faster functions */
	{
		int one = 1;
		formatdef *native = native_table;
		formatdef *other, *ptr;
		if ((int)*(unsigned char*)&one)
			other = lilendian_table;
		else
			other = bigendian_table;
		/* Scan through the native table, find a matching
		   entry in the endian table and swap in the
		   native implementations whenever possible
		   (64-bit platforms may not have "standard" sizes) */
		while (native->format != '\0' && other->format != '\0') {
			ptr = other;
			while (ptr->format != '\0') {
				if (ptr->format == native->format) {
					/* Match faster when formats are
					   listed in the same order */
					if (ptr == other)
						other++;
					/* Only use the trick if the
					   size matches */
					if (ptr->size != native->size)
						break;
					/* Skip float and double, could be
					   "unknown" float format */
					if (ptr->format == 'd' || ptr->format == 'f')
						break;
					ptr->pack = native->pack;
					ptr->unpack = native->unpack;
					break;
				}
				ptr++;
			}
			native++;
		}
	}
#endif

	/* Add some symbolic constants to the module */
	if (StructError == NULL) {
		StructError = PyErr_NewException("struct.error", NULL, NULL);
		if (StructError == NULL)
			return NULL;
	}

	Py_INCREF(StructError);
	PyModule_AddObject(m, "error", StructError);

	Py_INCREF((PyObject*)&PyStructType);
	PyModule_AddObject(m, "Struct", (PyObject*)&PyStructType);

	PyModule_AddObject(m, "__version__", ver);

	PyModule_AddIntConstant(m, "_PY_STRUCT_RANGE_CHECKING", 1);
#ifdef PY_STRUCT_OVERFLOW_MASKING
	PyModule_AddIntConstant(m, "_PY_STRUCT_OVERFLOW_MASKING", 1);
#endif
#ifdef PY_STRUCT_FLOAT_COERCE
	PyModule_AddIntConstant(m, "_PY_STRUCT_FLOAT_COERCE", 1);
#endif
	return m;

}
