How to create a Ruby extension in C in under 5 minutes

By Peter Cooper

Many coders will reach a situation where developing a C extension makes sense, whether for doing 'heavy lifting', diving into assembly language, interfacing with other C code, etc. Luckily, developing a basic Ruby extension in C is easy.

Note: This article assumes you are using a UNIX of some sort (this was all tested on OS X) and that you have Ruby installed properly (from source, ideally, so you have ruby.h available). If not, you may be stuck.

First, create a directory called MyTest (or whatever you want your extension to be called) and in there create two files, extconf.rb and MyTest.c (if you want to download pre-written sources, they're in this tar file). In extconf.rb, put the following:

require ' mkmf ' extension_name = ' mytest ' dir_config ( extension_name ) create_makefile ( extension_name )

This code is pretty self descriptive. It loads up Ruby's makefile library, sets up the environment, and creates a Makefile. Next, create the actual extension in MyTest.c. Here's some demonstration code to create a basic module with a single method called 'test1' which returns '10' when called:

// Include the Ruby headers and goodies #include "ruby.h" // Defining a space for information and references about the module to be stored internally VALUE MyTest = Qnil; // Prototype for the initialization method - Ruby calls this, not you void Init_mytest(); // Prototype for our method 'test1' - methods are prefixed by 'method_' here VALUE method_test1(VALUE self); // The initialization method for this module void Init_mytest() { MyTest = rb_define_module("MyTest"); rb_define_method(MyTest, "test1", method_test1, 0); } // Our 'test1' method.. it simply returns a value of '10' for now. VALUE method_test1(VALUE self) { int x = 10; return INT2NUM(x); }

For C, it's reasonably simple code. We include the Ruby headers via ruby.h, set up a variable to store the module in, and create two functions, one which is called by Ruby when it initiates the module, and the other is our test1 method (Note that in the code above we define MyTest as a module, but you could just as easily use rb_define_class to create a class, if that's what you wanted to do.)

Next we need to compile our hard work. Make sure you're in the MyTest directory and run ruby extconf.rb, and it should say that the Makefile has been created. If so, you can then run make to compile and build the extension. As long as no errors occur, run up irb (or create a new Ruby program) and test out your newly build extension like so:

irb(main):001:0> require 'mytest' => true irb(main):002:0> include MyTest => Object irb(main):003:0> puts test1 10

Et voila! The world's simplest Ruby extension written in C in under 5 minutes. It doesn't do much, it's overly basic, but this is the springboard to greater things :)