In article <86bs5luk1m.fsf / squash.oucs.ox.ac.uk>,
Simon Cozens  <simon / ermine.ox.ac.uk> wrote:
>ptkwt / shell1.aracnet.com (Phil Tomson) writes:
>> Hmmmm.... interesting idea.  So basically what you're proposing would be 
>> able to walk the AST of the currently running program (or any arbitrary 
>> snippet that you send off to eval?)?  
>
>Yes. That's what Perl's B.pm does.
>
> % perl -MB -le '$x= B::main_start; print $x->name while $x=$x->next'
>nextstate
>pushmark
>gv
>entersub
>gvsv
>sassign
>...
>
>(New statement, add a mark to the stack, add a symbol table entry
>[B::main_start] to the stack, call it, put a variable on the stack,
>assign the result of the call to the variable...)
>
>> I don't think anyone has approached the problem in the way you propose.
>> Can you give some more details of how you're thinking of doing it?
>
>I can even give you some sample code, because I've already got a fair bit
>of it working. :) 
>
>It says a lot for Ruby's ease of use, clarity of code and
>well-developed extensions system that I've only been *using* the
>bloody language for three days and I've already got most of a bytecode
>walker constructed.
>
>Here's the core of it:
>
>static VALUE
>bytecode_get_root(VALUE class)
>{
>    return Data_Wrap_Struct(class, 0, 0, ruby_eval_tree);
>}
>
>void Init_Bytecode () {
>    cByteNode = rb_define_class("ByteNode", rb_cObject);
>    rb_define_singleton_method(cByteNode, "root", bytecode_get_root, 0);
>    rb_define_method(cByteNode, "type", bytecode_nd_type, 0);
>    rb_define_method(cByteNode, "line", bytecode_nd_line, 0);
>    rb_define_method(cByteNode, "head", bytecode_nd_head, 0);
>    rb_define_method(cByteNode, "next", bytecode_nd_next, 0);
>    ...
>}
>
>The bytecode_nd_* functions just do a Data_Get_Struct, call the relevant
>nd_* macro, and wrap the result.
>
>Now I can say:
>
>% ruby -e 'require "Bytecode"; p ByteNode.root; p ByteNode.root.next.type'
>#<ByteNode:0x401a6550>
>4
>

I wonder if we could do this a lot faster by using swig to wrap the 
Ruby C parser?  Swig Ruby itself to make an extension for Ruby.

....just a thought.

Phil