223: def self.run blk=nil, tail=nil, &block
224: @tails ||= []
225: tail and @tails.unshift(tail)
226:
227: if reactor_running?
228: (b = blk || block) and b.call
229: else
230: @conns = {}
231: @acceptors = {}
232: @timers = {}
233: @wrapped_exception = nil
234: begin
235: @reactor_running = true
236: initialize_event_machine
237: (b = blk || block) and add_timer(0, b)
238: if @next_tick_queue && !@next_tick_queue.empty?
239: add_timer(0) { signal_loopbreak }
240: end
241: @reactor_thread = Thread.current
242: run_machine
243: ensure
244: begin
245: release_machine
246: ensure
247: if @threadpool
248: @threadpool.each { |t| t.exit }
249: @threadpool.each { |t| t.kill! if t.alive? }
250: @threadqueue = nil
251: @resultqueue = nil
252: end
253: @threadpool = nil
254: @next_tick_queue = nil
255: end
256: @reactor_running = false
257: @reactor_thread = nil
258: end
259:
260: until @tails.empty?
261: @tails.pop.call
262: end
263:
264: raise @wrapped_exception if @wrapped_exception
265: end
266: end