From: Charles Oliver Nutter Date: 2009-01-13T06:31:15+09:00 Subject: Re: Binding.of_caller examples don't work. Ken Bloom wrote: > My goal is that other threads don't see the changes, by operating as > follows: > > In Ruby 1.8 pseudocode: > > old_critical=Thread.critical > begin > Thread.critical=true > > [Fixnum,String].each{|klass| override_methods_on klass} > result=builderblock.call > [Fixnum,String].each{|klass| restore_methods_on klass} > ensure > Thread.critical=old_critical > end > > Can I guarantee that other threads won't see my badly mangled Fixnum and > String? Or is there some possiblity that another thread would continue > executing and call (now badly broken) methods on Fixnum and String for a > while before it hit a checkpoint that made it hit the lock? From your > description it sounds like the latter is the case, in which case I need > to be looking at sandboxing solutions or warn people very loudly that > this part of the library is not thread safe and cannot be made thread > safe. (AIUI, there's also no standard way of sandboxing right now.) The latter...you can't guarantee the other threads will necessarily stop before they see your breaking changes. You need to look at sandboxing, or help Matz implement selector namespaces (which I'd love to help with too). > In Ruby 1.9 pesudocode this is only slightly different: > > Thread.exclusive do > [Fixnum,String].each{|klass| override_methods_on klass} > result=builderblock.call > [Fixnum,String].each{|klass| restore_methods_on klass} > end This only guarantees only one thread can execute that block of code; it doesn't stop other threads from running: ◆ ruby1.9 -e "require 'thread'; Thread.new { sleep 1; puts 'hello'; redo }; Thread.exclusive do; sleep; end" hello hello hello hello hello ^C - Charlie