]> Sergey Matveev's repositories - public-inbox.git/commitdiff
ds: stop distinguishing event read and write callbacks
authorEric Wong <e@80x24.org>
Sun, 16 Jun 2019 06:11:28 +0000 (06:11 +0000)
committerEric Wong <e@80x24.org>
Sun, 16 Jun 2019 06:36:46 +0000 (06:36 +0000)
Having separate read/write callbacks in every class is too
confusing to my easily-confused mind.  Instead, give every class
an "event_step" callback which is easier to wrap my head around.

This will make future code to support IO::Socket::SSL-wrapped
sockets easier-to-digest, since SSL_write() can require waiting
on POLLIN events, and SSL_read() can require waiting on POLLOUT
events.

lib/PublicInbox/DS.pm
lib/PublicInbox/EvCleanup.pm
lib/PublicInbox/HTTP.pm
lib/PublicInbox/HTTPD/Async.pm
lib/PublicInbox/Listener.pm
lib/PublicInbox/NNTP.pm
lib/PublicInbox/ParentPipe.pm

index 2f028a36a47db97bc8f8c0c4acb3f8e95502e835..2b04886ab50e171c57187ee80ec01977e207c497 100644 (file)
@@ -239,21 +239,6 @@ sub RunTimers {
     return $timeout;
 }
 
-sub event_step ($) {
-    my ($self) = @_;
-    return if $self->{closed};
-
-    my $wbuf = $self->{wbuf};
-    if (@$wbuf) {
-        $self->event_write;
-        return if $self->{closed} || scalar(@$wbuf);
-    }
-
-    # only read more requests if we've drained the write buffer,
-    # otherwise we can be buffering infinitely w/o backpressure
-    $self->event_read;
-}
-
 ### The epoll-based event loop. Gets installed as EventLoop if IO::Epoll loads
 ### okay.
 sub EpollEventLoop {
@@ -267,13 +252,11 @@ sub EpollEventLoop {
         # get up to 1000 events
         my $evcount = epoll_wait($Epoll, 1000, $timeout, \@events);
         for ($i=0; $i<$evcount; $i++) {
-            my $ev = $events[$i];
-
             # it's possible epoll_wait returned many events, including some at the end
             # that ones in the front triggered unregister-interest actions.  if we
             # can't find the %sock entry, it's because we're no longer interested
             # in that event.
-            event_step($DescriptorMap{$ev->[0]});
+            $DescriptorMap{$events[$i]->[0]}->event_step;
         }
         return unless PostEventLoop();
     }
@@ -316,9 +299,7 @@ sub PollEventLoop {
         # Fetch handles with read events
         while (@poll) {
             my ($fd, $state) = splice(@poll, 0, 2);
-            next unless $state;
-
-            event_step($DescriptorMap{$fd});
+            $DescriptorMap{$fd}->event_step if $state;
         }
 
         return unless PostEventLoop();
@@ -345,8 +326,7 @@ sub KQueueEventLoop {
         }
 
         foreach my $kev (@ret) {
-            my ($fd, $filter, $flags, $fflags) = @$kev;
-            event_step($DescriptorMap{$fd});
+            $DescriptorMap{$kev->[0]}->event_step;
         }
         return unless PostEventLoop();
     }
@@ -647,27 +627,6 @@ sub on_incomplete_write {
     $self->watch_write(1);
 }
 
-=head2 (VIRTUAL) C<< $obj->event_read() >>
-
-Readable event handler. Concrete deriviatives of PublicInbox::DS should
-provide an implementation of this. The default implementation is a noop
-if called.
-
-=cut
-sub event_read {} # noop
-
-=head2 C<< $obj->event_write() >>
-
-Writable event handler. Concrete deriviatives of PublicInbox::DS may wish to
-provide an implementation of this. The default implementation calls
-C<write()> with an C<undef>.
-
-=cut
-sub event_write {
-    my $self = shift;
-    $self->write(undef);
-}
-
 =head2 C<< $obj->watch_read( $boolean ) >>
 
 Turn 'readable' event notification on or off.
index f76fb68159cb97530d0d7ea10b023dfcdd9daa4c..c64e2388512508cfea87624007adce585eadfc24 100644 (file)
@@ -25,7 +25,7 @@ sub once_init () {
        fcntl($w, 1031, 4096) if $^O eq 'linux'; # 1031: F_SETPIPE_SZ
        $self->SUPER::new($w);
 
-       # always writable, since PublicInbox::EvCleanup::event_write
+       # always writable, since PublicInbox::EvCleanup::event_step
        # never drains wbuf.  We can avoid wasting a hash slot by
        # stuffing the read-end of the pipe into the never-to-be-touched
        # wbuf
@@ -57,7 +57,7 @@ sub _run_later () {
 }
 
 # Called by PublicInbox::DS
-sub event_write {
+sub event_step {
        my ($self) = @_;
        $self->watch_write(0);
        _run_asap();
index 4fbc34ee4768e6be3ef61c131046e518f54a4906..45bf23ec086702594cd0eed85298d4d52adb01b9 100644 (file)
@@ -64,10 +64,18 @@ sub new ($$$) {
        $self;
 }
 
-sub event_read { # called by PublicInbox::DS
+sub event_step { # called by PublicInbox::DS
        my ($self) = @_;
 
-       return event_read_input($self) if defined $self->{env};
+       my $wbuf = $self->{wbuf};
+       if (@$wbuf) {
+               $self->write(undef);
+               return if $self->{closed} || scalar(@$wbuf);
+       }
+       # only read more requests if we've drained the write buffer,
+       # otherwise we can be buffering infinitely w/o backpressure
+
+       return read_input($self) if defined $self->{env};
 
        my $off = length($self->{rbuf});
        my $r = sysread($self->{sock}, $self->{rbuf}, 8192, $off);
@@ -101,13 +109,14 @@ sub rbuf_process {
        my $len = input_prepare($self, \%env);
        defined $len or return write_err($self, undef); # EMFILE/ENFILE
 
-       $len ? event_read_input($self) : app_dispatch($self);
+       $len ? read_input($self) : app_dispatch($self);
 }
 
-sub event_read_input ($) {
+sub read_input ($) {
        my ($self) = @_;
        my $env = $self->{env};
-       return event_read_input_chunked($self) if env_chunked($env);
+       return if $env->{REMOTE_ADDR}; # in app dispatch
+       return read_input_chunked($self) if env_chunked($env);
 
        # env->{CONTENT_LENGTH} (identity)
        my $sock = $self->{sock};
@@ -229,7 +238,6 @@ sub identity_wcb ($) {
 
 sub next_request ($) {
        my ($self) = @_;
-       $self->watch_write(0);
        if ($self->{rbuf} eq '') { # wait for next request
                $self->watch_read(1);
        } else { # avoid recursion for pipelined requests
@@ -392,7 +400,7 @@ sub write_in_full {
        $rv
 }
 
-sub event_read_input_chunked { # unlikely...
+sub read_input_chunked { # unlikely...
        my ($self) = @_;
        my $input = $self->{env}->{'psgi.input'};
        my $sock = $self->{sock};
index 4d0c8d5bc93eb86182888e3e10d570857ea2d121..604627ab0b5678dfa99f43bfccc88af0b0c730b9 100644 (file)
@@ -75,7 +75,7 @@ sub async_pass {
        $self->{cb} = main_cb($http, $fh, $bref);
 }
 
-sub event_read { $_[0]->{cb}->(@_) }
+sub event_step { $_[0]->{cb}->(@_) }
 
 sub close {
        my $self = shift;
index a75a6fd9964ed1c9c2d2780b6680aa1b39ee76b2..6ee3abb1e27bed242d84ca069e827025e8370e15 100644 (file)
@@ -23,7 +23,7 @@ sub new ($$$) {
        $self
 }
 
-sub event_read {
+sub event_step {
        my ($self) = @_;
        my $sock = $self->{sock};
 
index fa412f8c6c8bc893b84ed80cb668cc45522a6fb9..796ac74d87aa7236e0dfe300124baad77f2a7d78 100644 (file)
@@ -53,7 +53,7 @@ sub next_tick () {
                } else {
                        # pipelined request, we bypassed socket-readiness
                        # checks to get here:
-                       event_read($nntp);
+                       event_step($nntp);
 
                        # maybe there's more pipelined data, or we'll have
                        # to register it for socket-readiness notifications
@@ -964,17 +964,20 @@ sub do_more ($$) {
        do_write($self, $data);
 }
 
-sub event_write {
+sub event_step {
        my ($self) = @_;
-       update_idle_time($self);
-       # only continue watching for readability when we are done writing:
-       if ($self->write(undef) == 1 && !$self->{long_res}) {
-               $self->watch_read(1);
+       return if $self->{closed};
+
+       my $wbuf = $self->{wbuf};
+       if (@$wbuf) {
+               update_idle_time($self);
+               $self->write(undef);
+               return if $self->{closed} || scalar(@$wbuf);
        }
-}
+       return if $self->{long_res};
+       # only read more requests if we've drained the write buffer,
+       # otherwise we can be buffering infinitely w/o backpressure
 
-sub event_read {
-       my ($self) = @_;
        use constant LINE_MAX => 512; # RFC 977 section 2.3
        my $rbuf = \($self->{rbuf});
        my $r;
index 25f13a82fe77b9d1c44f2a904f6e06a6e55915a5..a9f05fc14a9fa86f7b4c18868b13ef4f7bba6e7c 100644 (file)
@@ -16,6 +16,6 @@ sub new ($$$) {
        $self;
 }
 
-sub event_read { $_[0]->{cb}->($_[0]) }
+sub event_step { $_[0]->{cb}->($_[0]) }
 
 1;