Bug #10786

SIGINT can not interrupt remaining codes after XMLRPC::Server gets SIGINT

Added by nidev (Changbeom Yun) over 4 years ago. Updated about 3 years ago.

Target version:
ruby -v:
ruby 2.2.0p0 (2014-12-25 revision 49005) [x86_64-linux]


When XMLRPC::Server has started completely, a user presses Ctrl-C to send SIGINT. XMLRPC::Server stops by SIGINT.

Assuming there are remaining codes to be run after XMLRPC::Server stops, When a user tries to press Ctrl-C again to interrupt, it doesn't function.

No exception is raised and a user has to wait until Ruby reaches the end of a program, because SIGINT doesn't work at all.

Code used for test:

require "xmlrpc/server"

rpcd =
puts "Wait 30 seconds in main thread"
sleep 30
puts "Done"

Reproducing procedure:

  1. Save above source into a Ruby file.
  2. Run it with Ruby.
  3. Wait until XMLRPC::Server(Actually, WEBrick) message 'INFO WEBrick::HTTPServer#start' appears.
  4. Press Ctrl-C. (At this time, WEBrick gets shut down.)
  5. When 'Wait 30 seconds in main thread' appears, press Ctrl-C again.


Updated by nidev (Changbeom Yun) over 4 years ago

In xmlrpc/server.rb line 585-586,

    signals = %w[INT TERM HUP] & Signal.list.keys
    signals.each { |signal| trap(signal) { @server.shutdown } }

I found signal traps. This code behaves correctly when XMLRPC::Server is the only one instance which runs alone.

SIGINT (and also other signals) may shutdown XMLRPC::Server if there's no remaining code under the line calling 'serve'.

However, Signal.trap() invoked by XMLRPC::Server.serve() still affects until Ruby reaches at the end of a ruby program.

I think it's reasonable that Signal.trap is considered and installed by a programmer depending on their need. In short, it should be optional.

--- /usr/lib/ruby/2.2.0/xmlrpc/server.rb    2013-12-07 19:27:27.000000000 +0900
+++ server.rb   2015-01-28 10:27:57.233466656 +0900
@@ -582,9 +582,6 @@
   # Call this after you have added all you handlers to the server.
   # This method starts the server to listen for XML-RPC requests and answer them.
   def serve
-    signals = %w[INT TERM HUP] & Signal.list.keys
-    signals.each { |signal| trap(signal) { @server.shutdown } }

Updated by hsbt (Hiroshi SHIBATA) about 3 years ago

  • Status changed from Open to Rejected

xmlrpc has been extracted

Also available in: Atom PDF