Multisession blocking repair repair collab/gmcharlt/multises-poll-wait-repair-repair
authorBill Erickson <berick@esilibrary.com>
Mon, 18 Mar 2013 15:30:07 +0000 (11:30 -0400)
committerBill Erickson <berick@esilibrary.com>
Mon, 18 Mar 2013 15:30:07 +0000 (11:30 -0400)
One call of session_reap was left unprotected from potential blocking.
This change moves the protection check down into the session_reap call
to cover the final exposed instance and prevent future mishaps.

Signed-off-by: Bill Erickson <berick@esilibrary.com>
src/perl/lib/OpenSRF/MultiSession.pm

index 504d441..bd7a907 100644 (file)
@@ -225,12 +225,10 @@ sub session_wait {
                        # block on the xmpp socket until data arrives
                        $xmpp->process(-1);
                        $self->session_reap;
-                       $self->session_reap while $self->check_post_reap_changes;
                }
                return $count;
        } else {
                while(($count = $self->session_reap) == 0 && $self->running) {
-                       $self->session_reap while $self->check_post_reap_changes;
                        # block on the xmpp socket until data arrives
                        $xmpp->process(-1);
                }
@@ -238,19 +236,21 @@ sub session_wait {
        }
 }
 
-# returns true if any running requests are marked as complete,
-# but does so without touching the underlying socket (note 
-# req->{complete} vs req->complete).  We do this so that checking
-# the state of the request does not affect the state of the 
-# request. With this, we can see if session_reap caused any state 
-# changes that were not accounted for within session_reap.
-sub check_post_reap_changes {
-       my $self = shift;
-       return 1 if grep { $_->{req}->{complete} } @{$self->{running}};
-       return 0;
+sub session_reap {
+    my $self = shift;
+    $self->_session_reap;
+
+    # if any requests are marked complete as a side effect of 
+    # _session_reap, re-run _session_reap.  note that we check
+    # for completeness without touching the underlying socket
+    # (req->{complete} vs req->complete) to avoid additional 
+    # unintended socket-touching side effects.
+    while (grep { $_->{req}->{complete} } @{$self->{running}}) {
+        $self->_session_reap;
+    }
 }
 
-sub session_reap {
+sub _session_reap {
        my $self = shift;
 
        my @done;