⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 typeobject.c

📁 python s60 1.4.5版本的源代码
💻 C
📖 第 1 页 / 共 5 页
字号:
		COPYSEQ(sq_repeat);
		COPYSEQ(sq_item);
		COPYSEQ(sq_slice);
		COPYSEQ(sq_ass_item);
		COPYSEQ(sq_ass_slice);
		COPYSEQ(sq_contains);
		COPYSEQ(sq_inplace_concat);
		COPYSEQ(sq_inplace_repeat);
	}

	if (type->tp_as_mapping != NULL && base->tp_as_mapping != NULL) {
		basebase = base->tp_base;
		if (basebase->tp_as_mapping == NULL)
			basebase = NULL;
		COPYMAP(mp_length);
		COPYMAP(mp_subscript);
		COPYMAP(mp_ass_subscript);
	}

	if (type->tp_as_buffer != NULL && base->tp_as_buffer != NULL) {
		basebase = base->tp_base;
		if (basebase->tp_as_buffer == NULL)
			basebase = NULL;
		COPYBUF(bf_getreadbuffer);
		COPYBUF(bf_getwritebuffer);
		COPYBUF(bf_getsegcount);
		COPYBUF(bf_getcharbuffer);
	}

	basebase = base->tp_base;

	COPYSLOT(tp_dealloc);
	COPYSLOT(tp_print);
	if (type->tp_getattr == NULL && type->tp_getattro == NULL) {
		type->tp_getattr = base->tp_getattr;
		type->tp_getattro = base->tp_getattro;
	}
	if (type->tp_setattr == NULL && type->tp_setattro == NULL) {
		type->tp_setattr = base->tp_setattr;
		type->tp_setattro = base->tp_setattro;
	}
	/* tp_compare see tp_richcompare */
	COPYSLOT(tp_repr);
	/* tp_hash see tp_richcompare */
	COPYSLOT(tp_call);
	COPYSLOT(tp_str);
	if (type->tp_flags & base->tp_flags & Py_TPFLAGS_HAVE_RICHCOMPARE) {
		if (type->tp_compare == NULL &&
		    type->tp_richcompare == NULL &&
		    type->tp_hash == NULL)
		{
			type->tp_compare = base->tp_compare;
			type->tp_richcompare = base->tp_richcompare;
			type->tp_hash = base->tp_hash;
		}
	}
	else {
		COPYSLOT(tp_compare);
	}
	if (type->tp_flags & base->tp_flags & Py_TPFLAGS_HAVE_ITER) {
		COPYSLOT(tp_iter);
		COPYSLOT(tp_iternext);
	}
	if (type->tp_flags & base->tp_flags & Py_TPFLAGS_HAVE_CLASS) {
		COPYSLOT(tp_descr_get);
		COPYSLOT(tp_descr_set);
		COPYSLOT(tp_init);
		COPYSLOT(tp_alloc);
		COPYSLOT(tp_free);
		COPYSLOT(tp_is_gc);
	}
}

staticforward int add_operators(PyTypeObject *);
staticforward int add_subclass(PyTypeObject *base, PyTypeObject *type);

DL_EXPORT(int)
PyType_Ready(PyTypeObject *type)
{
	PyObject *dict, *bases;
	PyTypeObject *base;
	int i, n;

	if (type->tp_flags & Py_TPFLAGS_READY) {
		assert(type->tp_dict != NULL);
		return 0;
		}
	assert((type->tp_flags & Py_TPFLAGS_READYING) == 0);

	type->tp_flags |= Py_TPFLAGS_READYING;

	/* Initialize tp_base (defaults to BaseObject unless that's us) */
	base = type->tp_base;
	if (base == NULL && type != &PyBaseObject_Type)
		base = type->tp_base = &PyBaseObject_Type;

	/* Initialize the base class */
	if (base && base->tp_dict == NULL) {
		if (PyType_Ready(base) < 0)
			goto error;
	}

	/* Initialize ob_type if NULL.  This means extensions that want to be
	   compilable separately on Windows can call PyType_Ready() instead of
	   initializing the ob_type field of their type objects. */
	if (type->ob_type == NULL)
		type->ob_type = base->ob_type;

	/* Initialize tp_bases */
	bases = type->tp_bases;
	if (bases == NULL) {
		if (base == NULL)
			bases = PyTuple_New(0);
		else
			bases = Py_BuildValue("(O)", base);
		if (bases == NULL)
			goto error;
		type->tp_bases = bases;
	}

	/* Initialize tp_dict */
	dict = type->tp_dict;
	if (dict == NULL) {
		dict = PyDict_New();
		if (dict == NULL)
			goto error;
		type->tp_dict = dict;
	}

	/* Add type-specific descriptors to tp_dict */
	if (add_operators(type) < 0)
		goto error;
	if (type->tp_methods != NULL) {
	  	// XXX:CW32
		if (add_methods(type, (PyMethodDef *)type->tp_methods) < 0)
			goto error;
	}
	if (type->tp_members != NULL) {
	  	// XXX:CW32
		if (add_members(type, (PyMemberDef *)type->tp_members) < 0)
			goto error;
	}
	if (type->tp_getset != NULL) {
		// XXX:CW32
		if (add_getset(type, (PyGetSetDef *)type->tp_getset) < 0)
			goto error;
	}

	/* Calculate method resolution order */
	if (mro_internal(type) < 0) {
		goto error;
	}

	/* Inherit special flags from dominant base */
	if (type->tp_base != NULL)
		inherit_special(type, type->tp_base);

	/* Initialize tp_dict properly */
	bases = type->tp_mro;
	assert(bases != NULL);
	assert(PyTuple_Check(bases));
	n = PyTuple_GET_SIZE(bases);
	for (i = 1; i < n; i++) {
		PyObject *b = PyTuple_GET_ITEM(bases, i);
		if (PyType_Check(b))
			inherit_slots(type, (PyTypeObject *)b);
	}

#ifndef SYMBIAN
	/* if the type dictionary doesn't contain a __doc__, set it from
	   the tp_doc slot.
	 */
	if (PyDict_GetItemString(type->tp_dict, "__doc__") == NULL) {
		if (type->tp_doc != NULL) {
			PyObject *doc = PyString_FromString(type->tp_doc);
			PyDict_SetItemString(type->tp_dict, "__doc__", doc);
			Py_DECREF(doc);
		} else {
			PyDict_SetItemString(type->tp_dict, "__doc__", Py_None);
		}
	}
#endif

	/* Some more special stuff */
	base = type->tp_base;
	if (base != NULL) {
		if (type->tp_as_number == NULL)
			type->tp_as_number = base->tp_as_number;
		if (type->tp_as_sequence == NULL)
			type->tp_as_sequence = base->tp_as_sequence;
		if (type->tp_as_mapping == NULL)
			type->tp_as_mapping = base->tp_as_mapping;
	}

	/* Link into each base class's list of subclasses */
	bases = type->tp_bases;
	n = PyTuple_GET_SIZE(bases);
	for (i = 0; i < n; i++) {
		PyObject *b = PyTuple_GET_ITEM(bases, i);
		if (PyType_Check(b) &&
		    add_subclass((PyTypeObject *)b, type) < 0)
			goto error;
	}

	/* All done -- set the ready flag */
	assert(type->tp_dict != NULL);
	type->tp_flags =
		(type->tp_flags & ~Py_TPFLAGS_READYING) | Py_TPFLAGS_READY;
	return 0;

  error:
	type->tp_flags &= ~Py_TPFLAGS_READYING;
	return -1;
}

static int
add_subclass(PyTypeObject *base, PyTypeObject *type)
{
	int i;
	PyObject *list, *ref, *new;

	list = base->tp_subclasses;
	if (list == NULL) {
		base->tp_subclasses = list = PyList_New(0);
		if (list == NULL)
			return -1;
	}
	assert(PyList_Check(list));
	new = PyWeakref_NewRef((PyObject *)type, NULL);
	i = PyList_GET_SIZE(list);
	while (--i >= 0) {
		ref = PyList_GET_ITEM(list, i);
		assert(PyWeakref_CheckRef(ref));
		if (PyWeakref_GET_OBJECT(ref) == Py_None)
			return PyList_SetItem(list, i, new);
	}
	i = PyList_Append(list, new);
	Py_DECREF(new);
	return i;
}


/* Generic wrappers for overloadable 'operators' such as __getitem__ */

/* There's a wrapper *function* for each distinct function typedef used
   for type object slots (e.g. binaryfunc, ternaryfunc, etc.).  There's a
   wrapper *table* for each distinct operation (e.g. __len__, __add__).
   Most tables have only one entry; the tables for binary operators have two
   entries, one regular and one with reversed arguments. */

static PyObject *
wrap_inquiry(PyObject *self, PyObject *args, void *wrapped)
{
	inquiry func = (inquiry)wrapped;
	int res;

	if (!PyArg_ParseTuple(args, ""))
		return NULL;
	res = (*func)(self);
	if (res == -1 && PyErr_Occurred())
		return NULL;
	return PyInt_FromLong((long)res);
}

static PyObject *
wrap_binaryfunc(PyObject *self, PyObject *args, void *wrapped)
{
	binaryfunc func = (binaryfunc)wrapped;
	PyObject *other;

	if (!PyArg_ParseTuple(args, "O", &other))
		return NULL;
	return (*func)(self, other);
}

static PyObject *
wrap_binaryfunc_l(PyObject *self, PyObject *args, void *wrapped)
{
	binaryfunc func = (binaryfunc)wrapped;
	PyObject *other;

	if (!PyArg_ParseTuple(args, "O", &other))
		return NULL;
	if (!(self->ob_type->tp_flags & Py_TPFLAGS_CHECKTYPES) &&
	    !PyType_IsSubtype(other->ob_type, self->ob_type)) {
		Py_INCREF(Py_NotImplemented);
		return Py_NotImplemented;
	}
	return (*func)(self, other);
}

static PyObject *
wrap_binaryfunc_r(PyObject *self, PyObject *args, void *wrapped)
{
	binaryfunc func = (binaryfunc)wrapped;
	PyObject *other;

	if (!PyArg_ParseTuple(args, "O", &other))
		return NULL;
	if (!(self->ob_type->tp_flags & Py_TPFLAGS_CHECKTYPES) &&
	    !PyType_IsSubtype(other->ob_type, self->ob_type)) {
		Py_INCREF(Py_NotImplemented);
		return Py_NotImplemented;
	}
	return (*func)(other, self);
}

static PyObject *
wrap_coercefunc(PyObject *self, PyObject *args, void *wrapped)
{
	coercion func = (coercion)wrapped;
	PyObject *other, *res;
	int ok;

	if (!PyArg_ParseTuple(args, "O", &other))
		return NULL;
	ok = func(&self, &other);
	if (ok < 0)
		return NULL;
	if (ok > 0) {
		Py_INCREF(Py_NotImplemented);
		return Py_NotImplemented;
	}
	res = PyTuple_New(2);
	if (res == NULL) {
		Py_DECREF(self);
		Py_DECREF(other);
		return NULL;
	}
	PyTuple_SET_ITEM(res, 0, self);
	PyTuple_SET_ITEM(res, 1, other);
	return res;
}

static PyObject *
wrap_ternaryfunc(PyObject *self, PyObject *args, void *wrapped)
{
	ternaryfunc func = (ternaryfunc)wrapped;
	PyObject *other;
	PyObject *third = Py_None;

	/* Note: This wrapper only works for __pow__() */

	if (!PyArg_ParseTuple(args, "O|O", &other, &third))
		return NULL;
	return (*func)(self, other, third);
}

static PyObject *
wrap_ternaryfunc_r(PyObject *self, PyObject *args, void *wrapped)
{
	ternaryfunc func = (ternaryfunc)wrapped;
	PyObject *other;
	PyObject *third = Py_None;

	/* Note: This wrapper only works for __pow__() */

	if (!PyArg_ParseTuple(args, "O|O", &other, &third))
		return NULL;
	return (*func)(other, self, third);
}

static PyObject *
wrap_unaryfunc(PyObject *self, PyObject *args, void *wrapped)
{
	unaryfunc func = (unaryfunc)wrapped;

	if (!PyArg_ParseTuple(args, ""))
		return NULL;
	return (*func)(self);
}

static PyObject *
wrap_intargfunc(PyObject *self, PyObject *args, void *wrapped)
{
	intargfunc func = (intargfunc)wrapped;
	int i;

	if (!PyArg_ParseTuple(args, "i", &i))
		return NULL;
	return (*func)(self, i);
}

static int
getindex(PyObject *self, PyObject *arg)
{
	int i;

	i = PyInt_AsLong(arg);
	if (i == -1 && PyErr_Occurred())
		return -1;
	if (i < 0) {
		// XXX:CW32
		PySequenceMethods *sq = (PySequenceMethods *)self->ob_type->tp_as_sequence;
		if (sq && sq->sq_length) {
			int n = (*sq->sq_length)(self);
			if (n < 0)
				return -1;
			i += n;
		}
	}
	return i;
}

static PyObject *
wrap_sq_item(PyObject *self, PyObject *args, void *wrapped)
{
	intargfunc func = (intargfunc)wrapped;
	PyObject *arg;
	int i;

	if (PyTuple_GET_SIZE(args) == 1) {
		arg = PyTuple_GET_ITEM(args, 0);
		i = getindex(self, arg);
		if (i == -1 && PyErr_Occurred())
			return NULL;
		return (*func)(self, i);
	}
	PyArg_ParseTuple(args, "O", &arg);
	assert(PyErr_Occurred());
	return NULL;
}

static PyObject *
wrap_intintargfunc(PyObject *self, PyObject *args, void *wrapped)
{
	intintargfunc func = (intintargfunc)wrapped;
	int i, j;

	if (!PyArg_ParseTuple(args, "ii", &i, &j))
		return NULL;
	return (*func)(self, i, j);
}

static PyObject *
wrap_sq_setitem(PyObject *self, PyObject *args, void *wrapped)
{
	intobjargproc func = (intobjargproc)wrapped;
	int i, res;
	PyObject *arg, *value;

	if (!PyArg_ParseTuple(args, "OO", &arg, &value))
		return NULL;
	i = getindex(self, arg);
	if (i == -1 && PyErr_Occurred())
		return NULL;
	res = (*func)(self, i, value);
	if (res == -1 && PyErr_Occurred())
		return NULL;
	Py_INCREF(Py_None);
	return Py_None;
}

static PyObject *
wrap_sq_delitem(PyObject *self, PyObject *args, void *wrapped)
{
	intobjargproc func = (intobjargproc)wrapped;
	int i, res;
	PyObject *arg;

	if (!PyArg_ParseTuple(args, "O", &arg))
		return NULL;
	i = getindex(self, arg);
	if (i == -1 && PyErr_Occurred())
		return NULL;
	res = (*func)(self, i, NULL);
	if (res == -1 && PyErr_Occurred())
		return NULL;
	Py_INCREF(Py_None);
	return Py_None;
}

static PyObject *
wrap_intintobjargproc(PyObject *self, PyObject *args, void *wrapped)
{
	intintobjargproc func = (intintobjargproc)wrapped;
	int i, j, res;
	PyObject *value;

	if (!PyArg_ParseTuple(args, "iiO", &i, &j, &value))
		return NULL;
	res = (*func)(self, i, j, value);
	if (res == -1 && PyErr_Occurred())
		return NULL;
	Py_INCREF(Py_None);
	return Py_None;
}

static PyObject *
wrap_delslice(PyObject *self, PyObject *args, void *wrapped)
{
	intintobjargproc func = (intintobjargproc)wrapped;
	int i, j, res;

	if (!PyArg_ParseTuple(args, "ii", &i, &j))
		return NULL;
	res = (*func)(self, i, j, NULL);
	if (res == -1 && PyErr_Occurred())
		return NULL;
	Py_INCREF(Py_None);
	return Py_None;
}

/* XXX objobjproc is a misnomer; should be objargpred */
static PyObject *
wrap_objobjproc(PyObject *self, PyObject *args, void *wrapped)
{
	objobjproc func = (objobjproc)wrapped;
	int res;
	PyObject *value;

	if (!PyArg_ParseTuple(args, "O", &value))
		return NULL;
	res = (*func)(self,

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -