# HG changeset patch
# User ZyX <[email protected]>
# Date 1367108862 -14400
# Branch python-extended-2
# Node ID 76f0957fb04d08fc04dd44ca2c78db13c9e992d4
# Parent  860ba5b056b1f13cc20b1c766e6e557cf0ac8964
Add iterator for vim.list and vim.bufferlist objects

diff -r 860ba5b056b1 -r 76f0957fb04d runtime/doc/if_pyth.txt
--- a/runtime/doc/if_pyth.txt   Sun Apr 28 03:54:27 2013 +0400
+++ b/runtime/doc/if_pyth.txt   Sun Apr 28 04:27:42 2013 +0400
@@ -214,6 +214,7 @@
            :py b = vim.buffers[i]      # Indexing (read-only)
            :py b in vim.buffers        # Membership test
            :py n = len(vim.buffers)    # Number of elements
+           :py for b in vim.buffers:   # Iterating over buffer list
 <
 vim.windows                                            *python-windows*
        A sequence object providing access to the list of vim windows.  The
diff -r 860ba5b056b1 -r 76f0957fb04d src/eval.c
--- a/src/eval.c        Sun Apr 28 03:54:27 2013 +0400
+++ b/src/eval.c        Sun Apr 28 04:27:42 2013 +0400
@@ -390,8 +390,6 @@
 static void clear_lval __ARGS((lval_T *lp));
 static void set_var_lval __ARGS((lval_T *lp, char_u *endp, typval_T *rettv, 
int copy, char_u *op));
 static int tv_op __ARGS((typval_T *tv1, typval_T *tv2, char_u  *op));
-static void list_add_watch __ARGS((list_T *l, listwatch_T *lw));
-static void list_rem_watch __ARGS((list_T *l, listwatch_T *lwrem));
 static void list_fix_watch __ARGS((list_T *l, listitem_T *item));
 static void ex_unletlock __ARGS((exarg_T *eap, char_u *argstart, int deep));
 static int do_unlet_var __ARGS((lval_T *lp, char_u *name_end, int forceit));
@@ -3106,7 +3104,7 @@
 /*
  * Add a watcher to a list.
  */
-    static void
+    void
 list_add_watch(l, lw)
     list_T     *l;
     listwatch_T        *lw;
@@ -3119,7 +3117,7 @@
  * Remove a watcher from a list.
  * No warning when it isn't found...
  */
-    static void
+    void
 list_rem_watch(l, lwrem)
     list_T     *l;
     listwatch_T        *lwrem;
diff -r 860ba5b056b1 -r 76f0957fb04d src/if_py_both.h
--- a/src/if_py_both.h  Sun Apr 28 03:54:27 2013 +0400
+++ b/src/if_py_both.h  Sun Apr 28 04:27:42 2013 +0400
@@ -531,66 +531,62 @@
 };
 
 /*
- * Buffer list object - Implementation
+ * Generic iterator object
  */
 
-static PyTypeObject BufMapType;
+static PyTypeObject IterType;
+
+typedef PyObject *(*nextfun)(void **);
+typedef void (*destructorfun)(void *);
+
+/* Main purpose of this object is removing the need for do python 
initialization 
+ * (i.e. PyType_Ready and setting type attributes) for a big bunch of objects.
+ */
 
 typedef struct
 {
     PyObject_HEAD
-} BufMapObject;
-
-    static PyInt
-BufMapLength(PyObject *self UNUSED)
+    void *cur;
+    nextfun next;
+    destructorfun destruct;
+} IterObject;
+
+    static PyObject *
+IterNew(void *start, destructorfun destruct, nextfun next)
 {
-    buf_T      *b = firstbuf;
-    PyInt      n = 0;
-
-    while (b)
-    {
-       ++n;
-       b = b->b_next;
-    }
-
-    return n;
+    IterObject *self;
+
+    self = PyObject_NEW(IterObject, &IterType);
+    self->cur = start;
+    self->next = next;
+    self->destruct = destruct;
+
+    return (PyObject *)(self);
 }
 
+    static void
+IterDestructor(PyObject *self)
+{
+    IterObject *this = (IterObject *)(self);
+
+    this->destruct(this->cur);
+
+    DESTRUCTOR_FINISH(self);
+}
+
     static PyObject *
-BufMapItem(PyObject *self UNUSED, PyObject *keyObject)
+IterNext(PyObject *self)
 {
-    buf_T      *b;
-    int                bnr;
-
-#if PY_MAJOR_VERSION < 3
-    if (PyInt_Check(keyObject))
-       bnr = PyInt_AsLong(keyObject);
-    else
-#endif
-    if (PyLong_Check(keyObject))
-       bnr = PyLong_AsLong(keyObject);
-    else
-    {
-       PyErr_SetString(PyExc_ValueError, _("key must be integer"));
-       return NULL;
-    }
-
-    b = buflist_findnr(bnr);
-
-    if (b)
-       return BufferNew(b);
-    else
-    {
-       PyErr_SetString(PyExc_KeyError, _("no such buffer"));
-       return NULL;
-    }
+    IterObject *this = (IterObject *)(self);
+
+    return this->next(&this->cur);
 }
 
-static PyMappingMethods BufMapAsMapping = {
-    (lenfunc)       BufMapLength,
-    (binaryfunc)    BufMapItem,
-    (objobjargproc) 0,
-};
+    static PyObject *
+IterIter(PyObject *self)
+{
+    return self;
+}
 
 typedef struct pylinkedlist_S {
     struct pylinkedlist_S      *pll_next;
@@ -990,6 +986,55 @@
     return list;
 }
 
+typedef struct
+{
+    listwatch_T        lw;
+    list_T     *list;
+} listiterinfo_T;
+
+    static void
+ListIterDestruct(listiterinfo_T *lii)
+{
+    list_rem_watch(lii->list, &lii->lw);
+    PyMem_Free(lii);
+}
+
+    static PyObject *
+ListIterNext(listiterinfo_T **lii)
+{
+    PyObject   *r;
+
+    if (!((*lii)->lw.lw_item))
+       return NULL;
+
+    if (!(r = ConvertToPyObject(&((*lii)->lw.lw_item->li_tv))))
+       return NULL;
+
+    (*lii)->lw.lw_item = (*lii)->lw.lw_item->li_next;
+
+    return r;
+}
+
+    static PyObject *
+ListIter(PyObject *self)
+{
+    listiterinfo_T     *lii;
+    list_T     *l = ((ListObject *) (self))->list;
+
+    if (!(lii = PyMem_New(listiterinfo_T, 1)))
+    {
+       PyErr_NoMemory();
+       return NULL;
+    }
+
+    list_add_watch(l, &lii->lw);
+    lii->lw.lw_item = l->lv_first;
+    lii->list = l;
+
+    return IterNew(lii,
+           (destructorfun) ListIterDestruct, (nextfun) ListIterNext);
+}
+
     static int
 ListAssItem(PyObject *self, Py_ssize_t index, PyObject *obj)
 {
@@ -2869,6 +2914,116 @@
     { NULL,        NULL,               0,          NULL }
 };
 
+/*
+ * Buffer list object - Implementation
+ */
+
+static PyTypeObject BufMapType;
+
+typedef struct
+{
+    PyObject_HEAD
+} BufMapObject;
+
+    static PyInt
+BufMapLength(PyObject *self UNUSED)
+{
+    buf_T      *b = firstbuf;
+    PyInt      n = 0;
+
+    while (b)
+    {
+       ++n;
+       b = b->b_next;
+    }
+
+    return n;
+}
+
+    static PyObject *
+BufMapItem(PyObject *self UNUSED, PyObject *keyObject)
+{
+    buf_T      *b;
+    int                bnr;
+
+#if PY_MAJOR_VERSION < 3
+    if (PyInt_Check(keyObject))
+       bnr = PyInt_AsLong(keyObject);
+    else
+#endif
+    if (PyLong_Check(keyObject))
+       bnr = PyLong_AsLong(keyObject);
+    else
+    {
+       PyErr_SetString(PyExc_ValueError, _("key must be integer"));
+       return NULL;
+    }
+
+    b = buflist_findnr(bnr);
+
+    if (b)
+       return BufferNew(b);
+    else
+    {
+       PyErr_SetString(PyExc_KeyError, _("no such buffer"));
+       return NULL;
+    }
+}
+
+    static void
+BufMapIterDestruct(PyObject *buffer)
+{
+    /* Iteration was stopped before all buffers were processed */
+    if (buffer)
+    {
+       Py_DECREF(buffer);
+    }
+}
+
+    static PyObject *
+BufMapIterNext(PyObject **buffer)
+{
+    PyObject   *next;
+    PyObject   *r;
+
+    if (!*buffer)
+       return NULL;
+
+    r = *buffer;
+
+    if (CheckBuffer((BufferObject *)(r)))
+    {
+       *buffer = NULL;
+       return NULL;
+    }
+
+    if (!((BufferObject *)(r))->buf->b_next)
+       next = NULL;
+    else if (!(next = BufferNew(((BufferObject *)(r))->buf->b_next)))
+       return NULL;
+    *buffer = next;
+    /* Do not increment reference: we no longer hold it (decref), but whoever 
on 
+     * other side will hold (incref). Decref+incref = nothing.
+     */
+    return r;
+}
+
+    static PyObject *
+BufMapIter(PyObject *self UNUSED)
+{
+    PyObject *buffer;
+
+    buffer = BufferNew(firstbuf);
+    return IterNew(buffer,
+           (destructorfun) BufMapIterDestruct, (nextfun) BufMapIterNext);
+}
+
+static PyMappingMethods BufMapAsMapping = {
+    (lenfunc)       BufMapLength,
+    (binaryfunc)    BufMapItem,
+    (objobjargproc) 0,
+};
+
 /* Current items object
  */
 
@@ -3383,6 +3538,14 @@
     OutputType.tp_setattr = OutputSetattr;
 #endif
 
+    vim_memset(&IterType, 0, sizeof(IterType));
+    IterType.tp_name = "vim.iter";
+    IterType.tp_basicsize = sizeof(IterObject);
+    IterType.tp_flags = Py_TPFLAGS_DEFAULT;
+    IterType.tp_doc = "generic iterator object";
+    IterType.tp_iter = IterIter;
+    IterType.tp_iternext = IterNext;
+
     vim_memset(&BufferType, 0, sizeof(BufferType));
     BufferType.tp_name = "vim.buffer";
     BufferType.tp_basicsize = sizeof(BufferType);
@@ -3426,6 +3589,7 @@
     BufMapType.tp_basicsize = sizeof(BufMapObject);
     BufMapType.tp_as_mapping = &BufMapAsMapping;
     BufMapType.tp_flags = Py_TPFLAGS_DEFAULT;
+    BufMapType.tp_iter = BufMapIter;
     BufferType.tp_doc = "vim buffer list";
 
     vim_memset(&WinListType, 0, sizeof(WinListType));
@@ -3492,6 +3656,7 @@
     ListType.tp_flags = Py_TPFLAGS_DEFAULT;
     ListType.tp_doc = "list pushing modifications to vim structure";
     ListType.tp_methods = ListMethods;
+    ListType.tp_iter = ListIter;
 #if PY_MAJOR_VERSION >= 3
     ListType.tp_getattro = ListGetattro;
     ListType.tp_setattro = ListSetattro;
diff -r 860ba5b056b1 -r 76f0957fb04d src/if_python.c
--- a/src/if_python.c   Sun Apr 28 03:54:27 2013 +0400
+++ b/src/if_python.c   Sun Apr 28 04:27:42 2013 +0400
@@ -1219,6 +1219,7 @@
     static char *(argv[2]) = {"/must>not&exist/foo", NULL};
 
     /* Fixups... */
+    PyType_Ready(&IterType);
     PyType_Ready(&BufferType);
     PyType_Ready(&RangeType);
     PyType_Ready(&WindowType);
diff -r 860ba5b056b1 -r 76f0957fb04d src/if_python3.c
--- a/src/if_python3.c  Sun Apr 28 03:54:27 2013 +0400
+++ b/src/if_python3.c  Sun Apr 28 04:27:42 2013 +0400
@@ -1519,6 +1519,7 @@
     /* The special value is removed from sys.path in Python3_Init(). */
     static wchar_t *(argv[2]) = {L"/must>not&exist/foo", NULL};
 
+    PyType_Ready(&IterType);
     PyType_Ready(&BufferType);
     PyType_Ready(&RangeType);
     PyType_Ready(&WindowType);
diff -r 860ba5b056b1 -r 76f0957fb04d src/proto/eval.pro
--- a/src/proto/eval.pro        Sun Apr 28 03:54:27 2013 +0400
+++ b/src/proto/eval.pro        Sun Apr 28 04:27:42 2013 +0400
@@ -127,4 +127,6 @@
 char_u *do_string_sub __ARGS((char_u *str, char_u *pat, char_u *sub, char_u 
*flags));
 int switch_win __ARGS((win_T **, tabpage_T **, win_T *, tabpage_T *));
 void restore_win __ARGS((win_T *, tabpage_T *));
+void list_add_watch __ARGS((list_T *l, listwatch_T *lw));
+void list_rem_watch __ARGS((list_T *l, listwatch_T *lwrem));
 /* vim: set ft=c : */

-- 
-- 
You received this message from the "vim_dev" maillist.
Do not top-post! Type your reply below the text you are replying to.
For more information, visit http://www.vim.org/maillist.php

--- 
You received this message because you are subscribed to the Google Groups 
"vim_dev" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
For more options, visit https://groups.google.com/groups/opt_out.


diff -cr vim.860ba5b056b1/runtime/doc/if_pyth.txt vim.76f0957fb04d/runtime/doc/if_pyth.txt
*** vim.860ba5b056b1/runtime/doc/if_pyth.txt	2013-04-28 20:33:28.266775056 +0400
--- vim.76f0957fb04d/runtime/doc/if_pyth.txt	2013-04-28 20:33:28.287774845 +0400
***************
*** 214,219 ****
--- 214,220 ----
  	    :py b = vim.buffers[i]	# Indexing (read-only)
  	    :py b in vim.buffers	# Membership test
  	    :py n = len(vim.buffers)	# Number of elements
+ 	    :py for b in vim.buffers:	# Iterating over buffer list
  <
  vim.windows						*python-windows*
  	A sequence object providing access to the list of vim windows.  The
diff -cr vim.860ba5b056b1/src/eval.c vim.76f0957fb04d/src/eval.c
*** vim.860ba5b056b1/src/eval.c	2013-04-28 20:33:28.263775086 +0400
--- vim.76f0957fb04d/src/eval.c	2013-04-28 20:33:28.284774875 +0400
***************
*** 390,397 ****
  static void clear_lval __ARGS((lval_T *lp));
  static void set_var_lval __ARGS((lval_T *lp, char_u *endp, typval_T *rettv, int copy, char_u *op));
  static int tv_op __ARGS((typval_T *tv1, typval_T *tv2, char_u  *op));
- static void list_add_watch __ARGS((list_T *l, listwatch_T *lw));
- static void list_rem_watch __ARGS((list_T *l, listwatch_T *lwrem));
  static void list_fix_watch __ARGS((list_T *l, listitem_T *item));
  static void ex_unletlock __ARGS((exarg_T *eap, char_u *argstart, int deep));
  static int do_unlet_var __ARGS((lval_T *lp, char_u *name_end, int forceit));
--- 390,395 ----
***************
*** 3106,3112 ****
  /*
   * Add a watcher to a list.
   */
!     static void
  list_add_watch(l, lw)
      list_T	*l;
      listwatch_T	*lw;
--- 3104,3110 ----
  /*
   * Add a watcher to a list.
   */
!     void
  list_add_watch(l, lw)
      list_T	*l;
      listwatch_T	*lw;
***************
*** 3119,3125 ****
   * Remove a watcher from a list.
   * No warning when it isn't found...
   */
!     static void
  list_rem_watch(l, lwrem)
      list_T	*l;
      listwatch_T	*lwrem;
--- 3117,3123 ----
   * Remove a watcher from a list.
   * No warning when it isn't found...
   */
!     void
  list_rem_watch(l, lwrem)
      list_T	*l;
      listwatch_T	*lwrem;
diff -cr vim.860ba5b056b1/src/if_py_both.h vim.76f0957fb04d/src/if_py_both.h
*** vim.860ba5b056b1/src/if_py_both.h	2013-04-28 20:33:28.250775216 +0400
--- vim.76f0957fb04d/src/if_py_both.h	2013-04-28 20:33:28.273774985 +0400
***************
*** 531,596 ****
  };
  
  /*
!  * Buffer list object - Implementation
   */
  
! static PyTypeObject BufMapType;
  
  typedef struct
  {
      PyObject_HEAD
! } BufMapObject;
  
!     static PyInt
! BufMapLength(PyObject *self UNUSED)
  {
!     buf_T	*b = firstbuf;
!     PyInt	n = 0;
  
!     while (b)
!     {
! 	++n;
! 	b = b->b_next;
!     }
  
!     return n;
  }
  
!     static PyObject *
! BufMapItem(PyObject *self UNUSED, PyObject *keyObject)
  {
!     buf_T	*b;
!     int		bnr;
  
! #if PY_MAJOR_VERSION < 3
!     if (PyInt_Check(keyObject))
! 	bnr = PyInt_AsLong(keyObject);
!     else
! #endif
!     if (PyLong_Check(keyObject))
! 	bnr = PyLong_AsLong(keyObject);
!     else
!     {
! 	PyErr_SetString(PyExc_ValueError, _("key must be integer"));
! 	return NULL;
!     }
  
!     b = buflist_findnr(bnr);
  
!     if (b)
! 	return BufferNew(b);
!     else
!     {
! 	PyErr_SetString(PyExc_KeyError, _("no such buffer"));
! 	return NULL;
!     }
  }
  
! static PyMappingMethods BufMapAsMapping = {
!     (lenfunc)       BufMapLength,
!     (binaryfunc)    BufMapItem,
!     (objobjargproc) 0,
! };
  
  typedef struct pylinkedlist_S {
      struct pylinkedlist_S	*pll_next;
--- 531,592 ----
  };
  
  /*
!  * Generic iterator object
   */
  
! static PyTypeObject IterType;
! 
! typedef PyObject *(*nextfun)(void **);
! typedef void (*destructorfun)(void *);
! 
! /* Main purpose of this object is removing the need for do python initialization 
!  * (i.e. PyType_Ready and setting type attributes) for a big bunch of objects.
!  */
  
  typedef struct
  {
      PyObject_HEAD
!     void *cur;
!     nextfun next;
!     destructorfun destruct;
! } IterObject;
  
!     static PyObject *
! IterNew(void *start, destructorfun destruct, nextfun next)
  {
!     IterObject *self;
  
!     self = PyObject_NEW(IterObject, &IterType);
!     self->cur = start;
!     self->next = next;
!     self->destruct = destruct;
  
!     return (PyObject *)(self);
  }
  
!     static void
! IterDestructor(PyObject *self)
  {
!     IterObject *this = (IterObject *)(self);
  
!     this->destruct(this->cur);
  
!     DESTRUCTOR_FINISH(self);
! }
  
!     static PyObject *
! IterNext(PyObject *self)
! {
!     IterObject *this = (IterObject *)(self);
! 
!     return this->next(&this->cur);
  }
  
!     static PyObject *
! IterIter(PyObject *self)
! {
!     return self;
! }
  
  typedef struct pylinkedlist_S {
      struct pylinkedlist_S	*pll_next;
***************
*** 990,995 ****
--- 986,1040 ----
      return list;
  }
  
+ typedef struct
+ {
+     listwatch_T	lw;
+     list_T	*list;
+ } listiterinfo_T;
+ 
+     static void
+ ListIterDestruct(listiterinfo_T *lii)
+ {
+     list_rem_watch(lii->list, &lii->lw);
+     PyMem_Free(lii);
+ }
+ 
+     static PyObject *
+ ListIterNext(listiterinfo_T **lii)
+ {
+     PyObject	*r;
+ 
+     if (!((*lii)->lw.lw_item))
+ 	return NULL;
+ 
+     if (!(r = ConvertToPyObject(&((*lii)->lw.lw_item->li_tv))))
+ 	return NULL;
+ 
+     (*lii)->lw.lw_item = (*lii)->lw.lw_item->li_next;
+ 
+     return r;
+ }
+ 
+     static PyObject *
+ ListIter(PyObject *self)
+ {
+     listiterinfo_T	*lii;
+     list_T	*l = ((ListObject *) (self))->list;
+ 
+     if (!(lii = PyMem_New(listiterinfo_T, 1)))
+     {
+ 	PyErr_NoMemory();
+ 	return NULL;
+     }
+ 
+     list_add_watch(l, &lii->lw);
+     lii->lw.lw_item = l->lv_first;
+     lii->list = l;
+ 
+     return IterNew(lii,
+ 	    (destructorfun) ListIterDestruct, (nextfun) ListIterNext);
+ }
+ 
      static int
  ListAssItem(PyObject *self, Py_ssize_t index, PyObject *obj)
  {
***************
*** 2869,2874 ****
--- 2914,3029 ----
      { NULL,	    NULL,		0,	    NULL }
  };
  
+ /*
+  * Buffer list object - Implementation
+  */
+ 
+ static PyTypeObject BufMapType;
+ 
+ typedef struct
+ {
+     PyObject_HEAD
+ } BufMapObject;
+ 
+     static PyInt
+ BufMapLength(PyObject *self UNUSED)
+ {
+     buf_T	*b = firstbuf;
+     PyInt	n = 0;
+ 
+     while (b)
+     {
+ 	++n;
+ 	b = b->b_next;
+     }
+ 
+     return n;
+ }
+ 
+     static PyObject *
+ BufMapItem(PyObject *self UNUSED, PyObject *keyObject)
+ {
+     buf_T	*b;
+     int		bnr;
+ 
+ #if PY_MAJOR_VERSION < 3
+     if (PyInt_Check(keyObject))
+ 	bnr = PyInt_AsLong(keyObject);
+     else
+ #endif
+     if (PyLong_Check(keyObject))
+ 	bnr = PyLong_AsLong(keyObject);
+     else
+     {
+ 	PyErr_SetString(PyExc_ValueError, _("key must be integer"));
+ 	return NULL;
+     }
+ 
+     b = buflist_findnr(bnr);
+ 
+     if (b)
+ 	return BufferNew(b);
+     else
+     {
+ 	PyErr_SetString(PyExc_KeyError, _("no such buffer"));
+ 	return NULL;
+     }
+ }
+ 
+     static void
+ BufMapIterDestruct(PyObject *buffer)
+ {
+     /* Iteration was stopped before all buffers were processed */
+     if (buffer)
+     {
+ 	Py_DECREF(buffer);
+     }
+ }
+ 
+     static PyObject *
+ BufMapIterNext(PyObject **buffer)
+ {
+     PyObject	*next;
+     PyObject	*r;
+ 
+     if (!*buffer)
+ 	return NULL;
+ 
+     r = *buffer;
+ 
+     if (CheckBuffer((BufferObject *)(r)))
+     {
+ 	*buffer = NULL;
+ 	return NULL;
+     }
+ 
+     if (!((BufferObject *)(r))->buf->b_next)
+ 	next = NULL;
+     else if (!(next = BufferNew(((BufferObject *)(r))->buf->b_next)))
+ 	return NULL;
+     *buffer = next;
+     /* Do not increment reference: we no longer hold it (decref), but whoever on 
+      * other side will hold (incref). Decref+incref = nothing.
+      */
+     return r;
+ }
+ 
+     static PyObject *
+ BufMapIter(PyObject *self UNUSED)
+ {
+     PyObject *buffer;
+ 
+     buffer = BufferNew(firstbuf);
+     return IterNew(buffer,
+ 	    (destructorfun) BufMapIterDestruct, (nextfun) BufMapIterNext);
+ }
+ 
+ static PyMappingMethods BufMapAsMapping = {
+     (lenfunc)       BufMapLength,
+     (binaryfunc)    BufMapItem,
+     (objobjargproc) 0,
+ };
+ 
  /* Current items object
   */
  
***************
*** 3383,3388 ****
--- 3538,3551 ----
      OutputType.tp_setattr = OutputSetattr;
  #endif
  
+     vim_memset(&IterType, 0, sizeof(IterType));
+     IterType.tp_name = "vim.iter";
+     IterType.tp_basicsize = sizeof(IterObject);
+     IterType.tp_flags = Py_TPFLAGS_DEFAULT;
+     IterType.tp_doc = "generic iterator object";
+     IterType.tp_iter = IterIter;
+     IterType.tp_iternext = IterNext;
+ 
      vim_memset(&BufferType, 0, sizeof(BufferType));
      BufferType.tp_name = "vim.buffer";
      BufferType.tp_basicsize = sizeof(BufferType);
***************
*** 3426,3431 ****
--- 3589,3595 ----
      BufMapType.tp_basicsize = sizeof(BufMapObject);
      BufMapType.tp_as_mapping = &BufMapAsMapping;
      BufMapType.tp_flags = Py_TPFLAGS_DEFAULT;
+     BufMapType.tp_iter = BufMapIter;
      BufferType.tp_doc = "vim buffer list";
  
      vim_memset(&WinListType, 0, sizeof(WinListType));
***************
*** 3492,3497 ****
--- 3656,3662 ----
      ListType.tp_flags = Py_TPFLAGS_DEFAULT;
      ListType.tp_doc = "list pushing modifications to vim structure";
      ListType.tp_methods = ListMethods;
+     ListType.tp_iter = ListIter;
  #if PY_MAJOR_VERSION >= 3
      ListType.tp_getattro = ListGetattro;
      ListType.tp_setattro = ListSetattro;
diff -cr vim.860ba5b056b1/src/if_python3.c vim.76f0957fb04d/src/if_python3.c
*** vim.860ba5b056b1/src/if_python3.c	2013-04-28 20:33:28.265775066 +0400
--- vim.76f0957fb04d/src/if_python3.c	2013-04-28 20:33:28.286774855 +0400
***************
*** 1519,1524 ****
--- 1519,1525 ----
      /* The special value is removed from sys.path in Python3_Init(). */
      static wchar_t *(argv[2]) = {L"/must>not&exist/foo", NULL};
  
+     PyType_Ready(&IterType);
      PyType_Ready(&BufferType);
      PyType_Ready(&RangeType);
      PyType_Ready(&WindowType);
diff -cr vim.860ba5b056b1/src/if_python.c vim.76f0957fb04d/src/if_python.c
*** vim.860ba5b056b1/src/if_python.c	2013-04-28 20:33:28.269775026 +0400
--- vim.76f0957fb04d/src/if_python.c	2013-04-28 20:33:28.290774815 +0400
***************
*** 1219,1224 ****
--- 1219,1225 ----
      static char *(argv[2]) = {"/must>not&exist/foo", NULL};
  
      /* Fixups... */
+     PyType_Ready(&IterType);
      PyType_Ready(&BufferType);
      PyType_Ready(&RangeType);
      PyType_Ready(&WindowType);
diff -cr vim.860ba5b056b1/src/proto/eval.pro vim.76f0957fb04d/src/proto/eval.pro
*** vim.860ba5b056b1/src/proto/eval.pro	2013-04-28 20:33:28.251775206 +0400
--- vim.76f0957fb04d/src/proto/eval.pro	2013-04-28 20:33:28.274774976 +0400
***************
*** 127,130 ****
--- 127,132 ----
  char_u *do_string_sub __ARGS((char_u *str, char_u *pat, char_u *sub, char_u *flags));
  int switch_win __ARGS((win_T **, tabpage_T **, win_T *, tabpage_T *));
  void restore_win __ARGS((win_T *, tabpage_T *));
+ void list_add_watch __ARGS((list_T *l, listwatch_T *lw));
+ void list_rem_watch __ARGS((list_T *l, listwatch_T *lwrem));
  /* vim: set ft=c : */

Raspunde prin e-mail lui