]> git.pld-linux.org Git - packages/vim.git/blob - 7.0.135
- updated to 0.7.3
[packages/vim.git] / 7.0.135
1 To: vim-dev@vim.org
2 Subject: Patch 7.0.135
3 Fcc: outbox
4 From: Bram Moolenaar <Bram@moolenaar.net>
5 Mime-Version: 1.0
6 Content-Type: text/plain; charset=ISO-8859-1
7 Content-Transfer-Encoding: 8bit
8 ------------
9
10 Patch 7.0.135
11 Problem:    Crash when garbage collecting list or dict with loop.
12 Solution:   Don't use DEL_REFCOUNT but don't recurse into Lists and
13             Dictionaries when freeing them in the garbage collector.
14             Also add allocated Dictionaries to the list of Dictionaries to
15             avoid leaking memory.
16 Files:      src/eval.c, src/proto/eval.pro, src/tag.c
17
18
19 *** ../vim-7.0.134/src/eval.c   Sun Oct 15 15:10:08 2006
20 --- src/eval.c  Sun Oct 15 22:30:09 2006
21 ***************
22 *** 191,198 ****
23   #define FC_RANGE    2         /* function accepts range */
24   #define FC_DICT           4           /* Dict function, uses "self" */
25   
26 - #define DEL_REFCOUNT  999999  /* list/dict is being deleted */
27
28   /*
29    * All user-defined functions are found in this hashtable.
30    */
31 --- 191,196 ----
32 ***************
33 *** 435,441 ****
34   static void set_ref_in_list __ARGS((list_T *l, int copyID));
35   static void set_ref_in_item __ARGS((typval_T *tv, int copyID));
36   static void dict_unref __ARGS((dict_T *d));
37 ! static void dict_free __ARGS((dict_T *d));
38   static dictitem_T *dictitem_alloc __ARGS((char_u *key));
39   static dictitem_T *dictitem_copy __ARGS((dictitem_T *org));
40   static void dictitem_remove __ARGS((dict_T *dict, dictitem_T *item));
41 --- 433,439 ----
42   static void set_ref_in_list __ARGS((list_T *l, int copyID));
43   static void set_ref_in_item __ARGS((typval_T *tv, int copyID));
44   static void dict_unref __ARGS((dict_T *d));
45 ! static void dict_free __ARGS((dict_T *d, int recurse));
46   static dictitem_T *dictitem_alloc __ARGS((char_u *key));
47   static dictitem_T *dictitem_copy __ARGS((dictitem_T *org));
48   static void dictitem_remove __ARGS((dict_T *dict, dictitem_T *item));
49 ***************
50 *** 4899,4905 ****
51                     {
52                         if (list_append_tv(l, &item->li_tv) == FAIL)
53                         {
54 !                           list_free(l);
55                             return FAIL;
56                         }
57                         item = item->li_next;
58 --- 4897,4903 ----
59                     {
60                         if (list_append_tv(l, &item->li_tv) == FAIL)
61                         {
62 !                           list_free(l, TRUE);
63                             return FAIL;
64                         }
65                         item = item->li_next;
66 ***************
67 *** 5299,5305 ****
68         EMSG2(_("E697: Missing end of List ']': %s"), *arg);
69   failret:
70         if (evaluate)
71 !           list_free(l);
72         return FAIL;
73       }
74   
75 --- 5297,5303 ----
76         EMSG2(_("E697: Missing end of List ']': %s"), *arg);
77   failret:
78         if (evaluate)
79 !           list_free(l, TRUE);
80         return FAIL;
81       }
82   
83 ***************
84 *** 5363,5370 ****
85   list_unref(l)
86       list_T *l;
87   {
88 !     if (l != NULL && l->lv_refcount != DEL_REFCOUNT && --l->lv_refcount <= 0)
89 !       list_free(l);
90   }
91   
92   /*
93 --- 5361,5368 ----
94   list_unref(l)
95       list_T *l;
96   {
97 !     if (l != NULL && --l->lv_refcount <= 0)
98 !       list_free(l, TRUE);
99   }
100   
101   /*
102 ***************
103 *** 5372,5385 ****
104    * Ignores the reference count.
105    */
106       void
107 ! list_free(l)
108 !     list_T *l;
109   {
110       listitem_T *item;
111   
112 -     /* Avoid that recursive reference to the list frees us again. */
113 -     l->lv_refcount = DEL_REFCOUNT;
114
115       /* Remove the list from the list of lists for garbage collection. */
116       if (l->lv_used_prev == NULL)
117         first_list = l->lv_used_next;
118 --- 5370,5381 ----
119    * Ignores the reference count.
120    */
121       void
122 ! list_free(l, recurse)
123 !     list_T  *l;
124 !     int           recurse;    /* Free Lists and Dictionaries recursively. */
125   {
126       listitem_T *item;
127   
128       /* Remove the list from the list of lists for garbage collection. */
129       if (l->lv_used_prev == NULL)
130         first_list = l->lv_used_next;
131 ***************
132 *** 5392,5398 ****
133       {
134         /* Remove the item before deleting it. */
135         l->lv_first = item->li_next;
136 !       listitem_free(item);
137       }
138       vim_free(l);
139   }
140 --- 5388,5397 ----
141       {
142         /* Remove the item before deleting it. */
143         l->lv_first = item->li_next;
144 !       if (recurse || (item->li_tv.v_type != VAR_LIST
145 !                                          && item->li_tv.v_type != VAR_DICT))
146 !           clear_tv(&item->li_tv);
147 !       vim_free(item);
148       }
149       vim_free(l);
150   }
151 ***************
152 *** 6113,6119 ****
153       for (dd = first_dict; dd != NULL; )
154         if (dd->dv_copyID != copyID)
155         {
156 !           dict_free(dd);
157             did_free = TRUE;
158   
159             /* restart, next dict may also have been freed */
160 --- 6118,6127 ----
161       for (dd = first_dict; dd != NULL; )
162         if (dd->dv_copyID != copyID)
163         {
164 !           /* Free the Dictionary and ordinary items it contains, but don't
165 !            * recurse into Lists and Dictionaries, they will be in the list
166 !            * of dicts or list of lists. */
167 !           dict_free(dd, FALSE);
168             did_free = TRUE;
169   
170             /* restart, next dict may also have been freed */
171 ***************
172 *** 6130,6136 ****
173       for (ll = first_list; ll != NULL; )
174         if (ll->lv_copyID != copyID && ll->lv_watch == NULL)
175         {
176 !           list_free(ll);
177             did_free = TRUE;
178   
179             /* restart, next list may also have been freed */
180 --- 6138,6147 ----
181       for (ll = first_list; ll != NULL; )
182         if (ll->lv_copyID != copyID && ll->lv_watch == NULL)
183         {
184 !           /* Free the List and ordinary items it contains, but don't recurse
185 !            * into Lists and Dictionaries, they will be in the list of dicts
186 !            * or list of lists. */
187 !           list_free(ll, FALSE);
188             did_free = TRUE;
189   
190             /* restart, next list may also have been freed */
191 ***************
192 *** 6223,6233 ****
193       d = (dict_T *)alloc(sizeof(dict_T));
194       if (d != NULL)
195       {
196 !       /* Add the list to the hashtable for garbage collection. */
197         if (first_dict != NULL)
198             first_dict->dv_used_prev = d;
199         d->dv_used_next = first_dict;
200         d->dv_used_prev = NULL;
201   
202         hash_init(&d->dv_hashtab);
203         d->dv_lock = 0;
204 --- 6234,6245 ----
205       d = (dict_T *)alloc(sizeof(dict_T));
206       if (d != NULL)
207       {
208 !       /* Add the list to the list of dicts for garbage collection. */
209         if (first_dict != NULL)
210             first_dict->dv_used_prev = d;
211         d->dv_used_next = first_dict;
212         d->dv_used_prev = NULL;
213 +       first_dict = d;
214   
215         hash_init(&d->dv_hashtab);
216         d->dv_lock = 0;
217 ***************
218 *** 6245,6252 ****
219   dict_unref(d)
220       dict_T *d;
221   {
222 !     if (d != NULL && d->dv_refcount != DEL_REFCOUNT && --d->dv_refcount <= 0)
223 !       dict_free(d);
224   }
225   
226   /*
227 --- 6257,6264 ----
228   dict_unref(d)
229       dict_T *d;
230   {
231 !     if (d != NULL && --d->dv_refcount <= 0)
232 !       dict_free(d, TRUE);
233   }
234   
235   /*
236 ***************
237 *** 6254,6269 ****
238    * Ignores the reference count.
239    */
240       static void
241 ! dict_free(d)
242 !     dict_T *d;
243   {
244       int               todo;
245       hashitem_T        *hi;
246       dictitem_T        *di;
247   
248 -     /* Avoid that recursive reference to the dict frees us again. */
249 -     d->dv_refcount = DEL_REFCOUNT;
250
251       /* Remove the dict from the list of dicts for garbage collection. */
252       if (d->dv_used_prev == NULL)
253         first_dict = d->dv_used_next;
254 --- 6266,6279 ----
255    * Ignores the reference count.
256    */
257       static void
258 ! dict_free(d, recurse)
259 !     dict_T  *d;
260 !     int           recurse;    /* Free Lists and Dictionaries recursively. */
261   {
262       int               todo;
263       hashitem_T        *hi;
264       dictitem_T        *di;
265   
266       /* Remove the dict from the list of dicts for garbage collection. */
267       if (d->dv_used_prev == NULL)
268         first_dict = d->dv_used_next;
269 ***************
270 *** 6283,6289 ****
271              * something recursive causing trouble. */
272             di = HI2DI(hi);
273             hash_remove(&d->dv_hashtab, hi);
274 !           dictitem_free(di);
275             --todo;
276         }
277       }
278 --- 6293,6302 ----
279              * something recursive causing trouble. */
280             di = HI2DI(hi);
281             hash_remove(&d->dv_hashtab, hi);
282 !           if (recurse || (di->di_tv.v_type != VAR_LIST
283 !                                            && di->di_tv.v_type != VAR_DICT))
284 !               clear_tv(&di->di_tv);
285 !           vim_free(di);
286             --todo;
287         }
288       }
289 ***************
290 *** 6734,6740 ****
291         EMSG2(_("E723: Missing end of Dictionary '}': %s"), *arg);
292   failret:
293         if (evaluate)
294 !           dict_free(d);
295         return FAIL;
296       }
297   
298 --- 6747,6753 ----
299         EMSG2(_("E723: Missing end of Dictionary '}': %s"), *arg);
300   failret:
301         if (evaluate)
302 !           dict_free(d, TRUE);
303         return FAIL;
304       }
305   
306 *** ../vim-7.0.134/src/proto/eval.pro   Fri Mar 24 23:16:28 2006
307 --- src/proto/eval.pro  Sun Oct 15 22:08:11 2006
308 ***************
309 *** 44,50 ****
310   extern char_u *get_user_var_name __ARGS((expand_T *xp, int idx));
311   extern list_T *list_alloc __ARGS((void));
312   extern void list_unref __ARGS((list_T *l));
313 ! extern void list_free __ARGS((list_T *l));
314   extern dictitem_T *dict_lookup __ARGS((hashitem_T *hi));
315   extern int list_append_dict __ARGS((list_T *list, dict_T *dict));
316   extern int garbage_collect __ARGS((void));
317 --- 44,50 ----
318   extern char_u *get_user_var_name __ARGS((expand_T *xp, int idx));
319   extern list_T *list_alloc __ARGS((void));
320   extern void list_unref __ARGS((list_T *l));
321 ! extern void list_free __ARGS((list_T *l, int recurse));
322   extern dictitem_T *dict_lookup __ARGS((hashitem_T *hi));
323   extern int list_append_dict __ARGS((list_T *list, dict_T *dict));
324   extern int garbage_collect __ARGS((void));
325 *** ../vim-7.0.134/src/tag.c    Sun Sep 10 13:56:06 2006
326 --- src/tag.c   Sun Oct 15 21:44:56 2006
327 ***************
328 *** 911,917 ****
329   
330                 set_errorlist(curwin, list, ' ');
331   
332 !               list_free(list);
333   
334                 cur_match = 0;          /* Jump to the first tag */
335             }
336 --- 911,917 ----
337   
338                 set_errorlist(curwin, list, ' ');
339   
340 !               list_free(list, TRUE);
341   
342                 cur_match = 0;          /* Jump to the first tag */
343             }
344 *** ../vim-7.0.134/src/version.c        Sun Oct 15 15:10:08 2006
345 --- src/version.c       Sun Oct 15 22:01:53 2006
346 ***************
347 *** 668,669 ****
348 --- 668,671 ----
349   {   /* Add new patch number below this line */
350 + /**/
351 +     135,
352   /**/
353
354 -- 
355 Well, you come from nothing, you go back to nothing...  What have you
356 lost?  Nothing!
357                                 -- Monty Python: The life of Brian
358
359  /// Bram Moolenaar -- Bram@Moolenaar.net -- http://www.Moolenaar.net   \\\
360 ///        sponsor Vim, vote for features -- http://www.Vim.org/sponsor/ \\\
361 \\\        download, build and distribute -- http://www.A-A-P.org        ///
362  \\\            help me help AIDS victims -- http://ICCF-Holland.org    ///
This page took 0.058574 seconds and 3 git commands to generate.