On Mon, Jul 07, 2003 at 02:03:42AM +0900, Mauricio Fern=E1ndez wrote:
> On Sun, Jul 06, 2003 at 11:51:04PM +0900, Pit Capitain wrote:
> > On 6 Jul 2003 at 21:23, ts wrote:
> >=20
> > > >>>>> "P" =3D=3D Pit Capitain <pit / capitain.de> writes:
> > >=20
> > > P> yes, I know that you hacked Ruby and that Matz is also working o=
n it,=20
> > > P> but for me using the PragProg Ruby installer on Windows nothing =
of=20
> > > P> those I can use right now.
> > >=20
> > >  Write an extension :
> > >=20
> > > (... demo of Guy's secret code in action ...)
> >=20
> > This is the real Guy Decoux we all love and respect!
> >=20
> > I know you can do it and maybe I would be able to do so, too, after=20
> > spending enough time on it. Thank you for trying to motivate me to=20
> > come up with my own solution. But I'm sure this won't happen. So I'll=
=20
> > be waiting for Matz's code. Maybe Nobu will find some time to tell me=
=20
> > why my pure Ruby solution doesn't work.
>=20
> The extension is easy to write (although you'll have to wait for Guy to
> check if my code is a time bomb :-):

Quick fix for the warnings attached:

batsman@tux-chan:~/src/override$ expand -t2 b.rb
#!/usr/bin/ruby
require 'override'

class C
   def m
      puts "original"
   end
end

C.new.m  # =3D> original

puts "=3D" * 20
class C
   override :m
   def m
      puts "before(1)"
      super
      puts "after(1)"
   end
end

C.new.m  # =3D> before(1), original, after(1)

puts "=3D" * 20
class C
   override :m
   def m
      puts "before(2)"
      super
      puts "after(2)"
   end
end

C.new.m  # =3D> before(2), before(1), original, after(1), after(2)
batsman@tux-chan:~/src/override$ ruby b.rb
original
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D
before(1)
original
after(1)
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D
before(2)
before(1)
original
after(1)
after(2)


--=20
 _           _                            =20
| |__   __ _| |_ ___ _ __ ___   __ _ _ __ =20
| '_ \ / _` | __/ __| '_ ` _ \ / _` | '_ \=20
| |_) | (_| | |_\__ \ | | | | | (_| | | | |
|_.__/ \__,_|\__|___/_| |_| |_|\__,_|_| |_|
	Running Debian GNU/Linux Sid (unstable)
batsman dot geo at yahoo dot com

No, that's wrong too.  Now there's a race condition between the rm and
the mv.  Hmm, I need more coffee.
	-- Guy Maor on Debian Bug#25228

#include <ruby.h>
#include <st.h>
#include <node.h>


static 
VALUE
class_override(VALUE self, VALUE symbols)
{
 int len;
 int i;
 VALUE meth;
 VALUE name;
 st_data_t data;
 NODE* node;
 
 NEWOBJ(proxy, struct RClass);
 OBJSETUP(proxy, rb_cClass, T_ICLASS);
 
 len = RARRAY(symbols)->len;

 proxy->iv_tbl = st_init_numtable(); /* not needed? */
 proxy->m_tbl = st_init_numtable();
 proxy->super = RCLASS(self)->super;

 RBASIC(proxy)->klass = RBASIC(self)->klass;
 
 for(i = 0; i < len; i++) {
	 meth = rb_ary_entry(symbols, i);
	 name = rb_funcall(meth, rb_intern("to_s"), 0);
	 if(!st_lookup(RCLASS(self)->m_tbl, rb_intern(RSTRING(name)->ptr), &data))
		 continue; /* should do something else?? */
	 st_insert(proxy->m_tbl, rb_intern(RSTRING(name)->ptr), data);
	 node = (NODE *)data;
	 node->nd_cnt++;
 }

 RCLASS(self)->super = proxy;
 OBJ_INFECT(proxy, self);
 
 return self;
}


void
Init_override()
{
  rb_define_method(rb_cClass, "override", class_override, -2);
}