From d806ab682a8e914345db3f2eede292f85745c98c Mon Sep 17 00:00:00 2001
From: Ken Manheimer <ken.manheimer@gmail.com>
Date: Tue, 29 Mar 2011 14:26:01 -0400
Subject: [PATCH] * allout.el (allout-hide-by-annotation, allout-flag-region):
 Reduce possibility of overlay leakage by making them volatile.

* allout-widgets.el (allout-widgets-tally): Define as nil so the hash is
not shared between buffers.  Mode initialization is responsible for giving
it a useful starting value.
(allout-item-span): Reduce possibility of overlay leakage by making them
volatile.
(allout-widgets-count-buttons-in-region): Add diagnostic function for
tracking down overlay leaks.
---
 lisp/ChangeLog         | 13 +++++++++++++
 lisp/allout-widgets.el | 16 +++++++++++++++-
 lisp/allout.el         |  5 +++--
 3 files changed, 31 insertions(+), 3 deletions(-)

diff --git a/lisp/ChangeLog b/lisp/ChangeLog
index dbd335b73dd..8e6e78c705e 100644
--- a/lisp/ChangeLog
+++ b/lisp/ChangeLog
@@ -1,3 +1,16 @@
+2011-03-29  Ken Manheimer  <ken.manheimer@gmail.com>
+
+	* allout.el (allout-hide-by-annotation, allout-flag-region):
+	Reduce possibility of overlay leakage by making them volatile.
+
+	* allout-widgets.el (allout-widgets-tally): Define as nil so the
+	hash is not shared between buffers.  Mode initialization is
+	responsible for giving it a useful starting value.
+	(allout-item-span): Reduce possibility of overlay leakage by
+	making them volatile.
+	(allout-widgets-count-buttons-in-region): Add diagnostic function
+	for tracking down button overlay leaks.
+
 2011-03-29  Leo Liu  <sdl.web@gmail.com>
 
 	* ido.el (ido-read-internal): Use the default history var
diff --git a/lisp/allout-widgets.el b/lisp/allout-widgets.el
index 47f181ab76b..ae4265bda1f 100644
--- a/lisp/allout-widgets.el
+++ b/lisp/allout-widgets.el
@@ -238,7 +238,7 @@ buffer, and tracking increases as new widgets are added and
 decreases as obsolete widgets are garbage collected."
   :type 'boolean
   :group 'allout-widgets-developer)
-(defvar allout-widgets-tally (make-hash-table :test 'eq :weakness 'key)
+(defvar allout-widgets-tally nil
   "Hash-table of existing allout widgets, for debugging.
 
 Table is maintained iff `allout-widgets-maintain-tally' is non-nil.
@@ -2100,6 +2100,7 @@ previously established or is not moved."
     (cond ((not overlay) (when start
                            (setq overlay (make-overlay start end nil t nil))
                            (overlay-put overlay 'button item-widget)
+                           (overlay-put overlay 'evaporate t)
                            (widget-put item-widget :span-overlay overlay)
                            t))
           ;; report:
@@ -2343,6 +2344,19 @@ The elements of LIST are not copied, just the list structure itself."
 	(while (consp list) (push (pop list) res))
 	(prog1 (nreverse res) (setcdr res list)))
     (car list)))
+;;;_  . allout-widgets-count-buttons-in-region (start end)
+(defun allout-widgets-count-buttons-in-region (start end)
+  "Debugging/diagnostic tool - count overlays with 'button' property in region."
+  (interactive "r")
+  (setq start (or start (point-min))
+        end (or end (point-max)))
+  (if (> start end) (let ((interim start)) (setq start end end interim)))
+  (let ((button-overlays (delq nil
+                               (mapcar (function (lambda (o)
+                                                   (if (overlay-get o 'button)
+                                                       o)))
+                                       (overlays-in start end)))))
+    (length button-overlays)))
 
 ;;;_ : Run unit tests:
 (defun allout-widgets-run-unit-tests ()
diff --git a/lisp/allout.el b/lisp/allout.el
index 3fb8ed7ccd5..736ec42718b 100644
--- a/lisp/allout.el
+++ b/lisp/allout.el
@@ -4489,8 +4489,9 @@ Topic exposure is marked with text-properties, to be used by
             ;; advance to just after end of this annotation:
             (setq next (allout-next-single-char-property-change
                         (point) 'allout-was-hidden nil end))
-            (overlay-put (make-overlay prev next nil 'front-advance)
-                         'category 'allout-exposure-category)
+            (let ((o (make-overlay prev next nil 'front-advance)))
+              (overlay-put o 'category 'allout-exposure-category)
+              (overlay-put o 'evaporate t))
             (allout-deannotate-hidden prev next)
             (setq prev next)
             (if next (goto-char next)))))
-- 
2.39.5