• Ken Rockot's avatar
    More consistent order for service process shutdown · c18bc463
    Ken Rockot authored
    Today, service processes self-terminate as soon as they detect peer
    closure on their main service pipe. This is detected on the IO thread
    and results in the immediate scheduling of a main-thread task to
    terminate the process.
    
    Meanwhile, service instances themselves also watch for peer closure on
    the same pipe and are notified on whichever thread runs the service (IO
    or main thread). This triggers immediate destruction of the service
    instance.
    
    Because there is no ordering guarantee between the two independent
    signal handlers, the net result is that during clean shutdown of a
    service process, the service instance's destructor may not run, or
    may run after shutdown has already started. This can be problematic
    if the service continues to operate and perform tasks that depend
    on a now-partially-shut-down process environment like the task
    scheduler.
    
    As a separate but related issue, the pipe-watching logic has been
    watching for peer closure when it should really be watching for an
    unreadable state (i.e., peer closure AND empty inbound queue). This
    means that service termination could race with messages still on the
    pipe unless developers are careful to synchronize their browser-side
    Remote's teardown against some kind of ack message from the service.
    
    This change does a bunch of stuff all at once to solve these problems:
    
    - Modifies ContentClient ServiceFactory APIs so that they populate a
      shared instance (two shared instances really, one for IO, one for
      main thread) rather than having embedders provide their own instance.
    - Gives UtilityThreadImpl and its internal (IO-thread-bound)
      ServiceBinderImpl their own ServiceFactory instances with
      clearly-defined ownership and lifetime.
    - Removes independent pipe watching logic from ServiceBinderImpl,
      instead having it track service instance lifetimes from both
      ServiceFactory instances.
    - Modifies ServiceFactory's pipe watching logic to watch for an
      unreadable pipe rather than for peer closure.
    
    The net result is that service processes which are cleanly shut down,
    meaning they neither crashed nor were reaped during full browser
    process shutdown, will always run their service's destructor before
    initiating shutdown.
    
    Bug: 1135957
    Change-Id: I16adbd7c98b4eb4333a92cd338643d4d5a9f2d6f
    Tbr: caseq@chromium.org
    Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/2503346
    Commit-Queue: Ken Rockot <rockot@google.com>
    Reviewed-by: default avatarKinuko Yasuda <kinuko@chromium.org>
    Cr-Commit-Position: refs/heads/master@{#821847}
    c18bc463
service_process_host_browsertest.cc 5.86 KB