C ext to Ruby interaction between a Module and a Class

U

unbewust

I'm presently writing C extension to Ruby (under and for Mac OS X).

i do have a Ruby Module called "ROSXUtils" and i want to return a
class coming from another C ext to Ruby. The class being RAliasFile.

i don't know exactly how to do that.

for the time being i've put the class RAliasFile under a sub-directory
"lib" of my ext/ (of the Module ROSXUtils) :

ext/
extconf.rb
lib/
extconf.rb
dll_p.c
dll_p.h
raliasfile.bundle
raliasfile.c
rosxutils.bundle
rosxutils.c
UnixUtils.c
UnixUtils.h


BUT, for the time being in order to use, from C, the RAliasFile class,
i'm obliged to use :

rb_eval_string("require '/absolute/path/to/raliasfile'");

then to return an instance of this class :

VALUE alias = rb_eval_string("RAliasFile.new(arg)");

this works but isn't elegant ???


what could be the best way to instantiate a class being a C ext to
Ruby from a module being also a C ext to Ruby ???


also is my dir hierarchy shown above the best way ?

i'd like better having the class RAliasFile included in the
rmosxutils.bundle...


any comment appreciated ;-)

Yvon
 
N

Nobuyoshi Nakada

Hi,

At Fri, 3 Aug 2007 20:05:01 +0900,
unbewust wrote in [ruby-talk:263179]:
for the time being i've put the class RAliasFile under a sub-directory
"lib" of my ext/ (of the Module ROSXUtils) :

Since Makefile generated by mkmf.rb will install script files
under lib, it's not good idea to use that name for another
extension.
BUT, for the time being in order to use, from C, the RAliasFile class,
i'm obliged to use :

rb_eval_string("require '/absolute/path/to/raliasfile'");

then to return an instance of this class :

VALUE alias = rb_eval_string("RAliasFile.new(arg)");

rb_require("raliasfile");
alias = rb_class_new_instance(1, &arg, rb_path2class("RAliasFile"));
i'd like better having the class RAliasFile included in the
rmosxutils.bundle...

A static library instead of a shared object will be created by
setting $static true in extconf.rb.
 
T

Tim Pease

BUT, for the time being in order to use, from C, the RAliasFile class,
i'm obliged to use :

rb_eval_string("require '/absolute/path/to/raliasfile'");


rb_require( "relative/path/to/raliasfile" );

My preference is relative paths. Eventually you'll want to release
this as a gem to other developers, and they might not have the exact
some directory structure that you do.

then to return an instance of this class :

VALUE alias = rb_eval_string("RAliasFile.new(arg)");

VALUE alias = rb_class_new_instance( 1, args, RAliasFile );

Where 1 is the number of arguments in the args array, args is the
array of arguments (as a VALUE*), and RAliasFile is a reference to the
class you would like to create.
also is my dir hierarchy shown above the best way ?

Unless you need separate modules, I would flatten your directory tree
-- i.e. consolidate all the files in your ext/lib folder up into the
ext folder.
any comment appreciated ;-)

Hope these were helpful suggestions.

Blessings,
TwP
 
U

unbewust

Unless you need separate modules, I would flatten your directory tree
-- i.e. consolidate all the files in your ext/lib folder up into the
ext folder.


no, no, because they are closely dependant...

in fact i want to make something like FileUtils (included in ruby now)
BUT for the files on Mac OS X.

that's to say being able to create alias file, alias record, put files
in the trash and letting the file manager and also the alias manager
knows where everything is.

this would allow to "untrash" a file and/or a directory...

thanks a lot !

Yvon
 
U

unbewust

rb_require( "relative/path/to/raliasfile" );

My preference is relative paths. Eventually you'll want to release
this as a gem to other developers, and they might not have the exact
some directory structure that you do.





VALUE alias = rb_class_new_instance( 1, args, RAliasFile );

Where 1 is the number of arguments in the args array, args is the
array of arguments (as a VALUE*), and RAliasFile is a reference to the
class you would like to create.




Unless you need separate modules, I would flatten your directory tree
-- i.e. consolidate all the files in your ext/lib folder up into the
ext folder.




Hope these were helpful suggestions.

Blessings,
TwP

OK with relative path this is OK now, the prob arroses because my ruby
file to test was in another folder.

BUT i still have prob with "rb_require('raf/raliasfile');" :
//make => rosxutils.c:105: warning: passing argument 1 of rb_require
makes pointer from integer without a cast
// run => ./sample.rb:124: [BUG] Segmentation fault

may be it's only the form of the argument in cause here ie 'raf/
raliasfile' (see make result).

remarks here my set-up is still with a sub-dir (renamed raf instead of
lib) :

ext/
extconf.rb
Makefile
raf/
dll_path.c
dll_path.h
extconf.rb
Makefile
raliasfile.bundle
RAliasFile.c
RAliasFile.o
rosxutils.bundle
rosxutils.c
rosxutils.o
sample.rb
UnixUtils.c
UnixUtils.h
UnixUtils.o

remarks also if i make use of rb_eval_string('relative path')
everything wents OK.

the prob with absolute path cames from my sample.rb file (then ruby
side) which wasn't, at that time in the dir ext...


NOW if I put everything in the same diretory and adding $static = true
in extconf.rb i get :

../sample.rb:124:in `mkAlias': undefined class/module RAliasFile
(ArgumentError)

i don't have any file to load except rosxutils

then is there a way to know, afterwards what's in a bundle file ???


thanks for your help !

obviously when a first version OK i'll release that as a gem...

Yvon
 
N

Nobuyoshi Nakada

Hi,

At Sat, 4 Aug 2007 18:10:02 +0900,
unbewust wrote in [ruby-talk:263323]:
BUT i still have prob with "rb_require('raf/raliasfile');" :
//make => rosxutils.c:105: warning: passing argument 1 of rb_require
makes pointer from integer without a cast

String literal in C must be enclosed with double-quotes, not
single-quotes. Multiple characters inside single-quotes would
be an OSX specific extension, perhaps inherited from old MacOS.
 
P

Phlip

Nobuyoshi said:
unbewust wrote:

String literal in C must be enclosed with double-quotes, not
single-quotes. Multiple characters inside single-quotes would
be an OSX specific extension, perhaps inherited from old MacOS.

It's not specifically an extension - it's a multiple byte character. The
literal 'riffraff' would form a long-long (on some architures), containing
those ASCII codes all packed into its bits.

That's why the compiler ignores any trailing characters that don't fit into
its integer type, then issues a bizarre complain't about converting an
integer to a pointer. "" decays to a pointer.
 
N

Nobuyoshi Nakada

Hi,

At Sat, 4 Aug 2007 22:39:22 +0900,
Phlip wrote in [ruby-talk:263340]:
It's not specifically an extension - it's a multiple byte character. The

I meant it would not be defined by C89, C99 nor K&R. In C++,
it is called as "multicharacter literal", but an
implementation-defined feature.
 
A

Alec Ross

In message said:
On 8/3/07, unbewust <[email protected]> wrote:
....

BUT i still have prob with "rb_require('raf/raliasfile');" :
//make => rosxutils.c:105: warning: passing argument 1 of rb_require
makes pointer from integer without a cast
// run => ./sample.rb:124: [BUG] Segmentation fault

may be it's only the form of the argument in cause here ie 'raf/
raliasfile' (see make result).

Would

"rb_require(\"raf/raliasfile\");"

help?

(I.e replace the single quotes w/ escaped double quotes, within the
double quoted string literal.)

HTH

Alec Ross
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,755
Messages
2,569,536
Members
45,007
Latest member
obedient dusk

Latest Threads

Top