Make StopIteration a sink state.  This is done by clearing out the
di_dict field when the end of the list is reached.  Also make the
error ("dictionary changed size during iteration") a sticky state.

Also remove the next() method -- one is supplied automatically by
PyType_Ready() because the tp_iternext slot is set.  That's a good
thing, because the implementation given here was buggy (it never
raised StopIteration).
diff --git a/Objects/dictobject.c b/Objects/dictobject.c
index d7bbef9..2619160 100644
--- a/Objects/dictobject.c
+++ b/Objects/dictobject.c
@@ -1916,7 +1916,7 @@
 
 typedef struct {
 	PyObject_HEAD
-	dictobject *di_dict;
+	dictobject *di_dict; /* Set to NULL when iterator is exhausted */
 	int di_used;
 	int di_pos;
 	binaryfunc di_select;
@@ -1940,52 +1940,35 @@
 static void
 dictiter_dealloc(dictiterobject *di)
 {
-	Py_DECREF(di->di_dict);
+	Py_XDECREF(di->di_dict);
 	PyObject_Del(di);
 }
 
 static PyObject *
-dictiter_next(dictiterobject *di, PyObject *args)
-{
-	PyObject *key, *value;
-
-	if (di->di_used != di->di_dict->ma_used) {
-		PyErr_SetString(PyExc_RuntimeError,
-				"dictionary changed size during iteration");
-		return NULL;
-	}
-	if (PyDict_Next((PyObject *)(di->di_dict), &di->di_pos, &key, &value)) {
-		return (*di->di_select)(key, value);
-	}
-	PyErr_SetObject(PyExc_StopIteration, Py_None);
-	return NULL;
-}
-
-static PyObject *
 dictiter_getiter(PyObject *it)
 {
 	Py_INCREF(it);
 	return it;
 }
 
-static PyMethodDef dictiter_methods[] = {
-	{"next",	(PyCFunction)dictiter_next,	METH_VARARGS,
-	 "it.next() -- get the next value, or raise StopIteration"},
-	{NULL,		NULL}		/* sentinel */
-};
-
 static PyObject *dictiter_iternext(dictiterobject *di)
 {
 	PyObject *key, *value;
 
+	if (di->di_dict == NULL)
+		return NULL;
+
 	if (di->di_used != di->di_dict->ma_used) {
 		PyErr_SetString(PyExc_RuntimeError,
 				"dictionary changed size during iteration");
+		di->di_used = -1; /* Make this state sticky */
 		return NULL;
 	}
-	if (PyDict_Next((PyObject *)(di->di_dict), &di->di_pos, &key, &value)) {
+	if (PyDict_Next((PyObject *)(di->di_dict), &di->di_pos, &key, &value))
 		return (*di->di_select)(key, value);
-	}
+
+	Py_DECREF(di->di_dict);
+	di->di_dict = NULL;
 	return NULL;
 }
 
@@ -2019,7 +2002,7 @@
 	0,					/* tp_weaklistoffset */
 	(getiterfunc)dictiter_getiter,		/* tp_iter */
 	(iternextfunc)dictiter_iternext,	/* tp_iternext */
-	dictiter_methods,			/* tp_methods */
+	0,					/* tp_methods */
 	0,					/* tp_members */
 	0,					/* tp_getset */
 	0,					/* tp_base */