Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
57 changes: 57 additions & 0 deletions ext/tcl_ruby/compat.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
/* contains basic macros to facilitate ruby 1.8 and ruby 1.9 compatibility */

#ifndef GUARD_COMPAT_H
#define GUARD_COMPAT_H

#include <ruby.h>

/* test for 1.9 */
#if !defined(RUBY_19) && defined(ROBJECT_EMBED_LEN_MAX)
# define RUBY_19
#endif

/* macros for backwards compatibility with 1.8 */
#ifndef RUBY_19
# define RCLASS_M_TBL(c) (RCLASS(c)->m_tbl)
# define RCLASS_SUPER(c) (RCLASS(c)->super)
# define RCLASS_IV_TBL(c) (RCLASS(c)->iv_tbl)
# define OBJ_UNTRUSTED OBJ_TAINTED
# include "st.h"
#endif

#ifdef RUBY_19
inline static VALUE
class_alloc(VALUE flags, VALUE klass)
{
rb_classext_t *ext = ALLOC(rb_classext_t);
NEWOBJ(obj, struct RClass);
OBJSETUP(obj, klass, flags);
obj->ptr = ext;
RCLASS_IV_TBL(obj) = 0;
RCLASS_M_TBL(obj) = 0;
RCLASS_SUPER(obj) = 0;
RCLASS_IV_INDEX_TBL(obj) = 0;
return (VALUE)obj;
}
#endif

inline static VALUE
create_class(VALUE flags, VALUE klass)
{
#ifdef RUBY_19
VALUE new_klass = class_alloc(flags, klass);
#else
NEWOBJ(new_klass, struct RClass);
OBJSETUP(new_klass, klass, flags);
#endif

return (VALUE)new_klass;
}

# define FALSE 0
# define TRUE 1

/* a useful macro. cannot use ordinary CLASS_OF as it does not return an lvalue */
#define KLASS_OF(c) (RBASIC(c)->klass)

#endif
17 changes: 9 additions & 8 deletions ext/tcl_ruby/tcl_ruby.c
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
#include <ruby.h>
#include <tcl.h>
#include "compat.h"

typedef struct {
Tcl_Interp *interp;
Expand All @@ -20,12 +21,12 @@ static VALUE rb_tcl_interp_send_begin(VALUE args) {
VALUE obj = rb_ary_entry(args, 0);
VALUE interp_receive_args = rb_ary_entry(args, 1);

VALUE result = rb_funcall2(obj, rb_intern("interp_receive"), RARRAY(interp_receive_args)->len, RARRAY(interp_receive_args)->ptr);
VALUE result = rb_funcall2(obj, rb_intern("interp_receive"), RARRAY_LEN(interp_receive_args), RARRAY_PTR(interp_receive_args));

tcl_interp_struct *tcl_interp;
Data_Get_Struct(obj, tcl_interp_struct, tcl_interp);

char *tcl_result = strdup(RSTRING(rb_value_to_s(result))->ptr);
char *tcl_result = strdup(RSTRING_PTR(rb_value_to_s(result)));
Tcl_SetResult(tcl_interp->interp, tcl_result, (Tcl_FreeProc *)free);

return Qtrue;
Expand All @@ -36,7 +37,7 @@ static VALUE rb_tcl_interp_send_rescue(VALUE args, VALUE error_info) {
tcl_interp_struct *tcl_interp;
Data_Get_Struct(obj, tcl_interp_struct, tcl_interp);

char *tcl_result = strdup(RSTRING(rb_value_to_s(error_info))->ptr);
char *tcl_result = strdup(RSTRING_PTR(rb_value_to_s(error_info)));
Tcl_SetResult(tcl_interp->interp, tcl_result, (Tcl_FreeProc *)free);

if (rb_obj_is_kind_of(error_info, rb_eSystemExit)) {
Expand Down Expand Up @@ -97,7 +98,7 @@ static VALUE rb_tcl_interp_eval(VALUE self, VALUE args) {
VALUE script = rb_ary_entry(args, 0);

int timeout = 0;
if (RARRAY(args)->len == 2) {
if (RARRAY_LEN(args) == 2) {
timeout = NUM2INT(rb_ary_entry(args, 1));
}
#else
Expand All @@ -119,7 +120,7 @@ static VALUE rb_tcl_interp_eval(VALUE self, VALUE script) {
}
#endif

int result = Tcl_Eval(tcl_interp->interp, RSTRING(rb_value_to_s(script))->ptr);
int result = Tcl_Eval(tcl_interp->interp, RSTRING_PTR(rb_value_to_s(script)));

VALUE error_class = rb_const_get(rb_const_get(rb_cObject, rb_intern("Tcl")), rb_intern("Error"));

Expand Down Expand Up @@ -150,7 +151,7 @@ static VALUE rb_tcl_interp_list_to_array(VALUE self, VALUE list) {
tcl_interp_struct *tcl_interp;
Data_Get_Struct(self, tcl_interp_struct, tcl_interp);

Tcl_Obj *string = Tcl_NewStringObj(RSTRING(rb_value_to_s(list))->ptr, -1);
Tcl_Obj *string = Tcl_NewStringObj(RSTRING_PTR(rb_value_to_s(list)), -1);
Tcl_IncrRefCount(string);

int list_length, i;
Expand Down Expand Up @@ -184,14 +185,14 @@ static VALUE rb_tcl_interp_array_to_list(VALUE self, VALUE array) {
tcl_interp_struct *tcl_interp;
Data_Get_Struct(self, tcl_interp_struct, tcl_interp);

int array_length = RARRAY(array)->len, i;
int array_length = RARRAY_LEN(array), i;

Tcl_Obj *list = Tcl_NewObj();
Tcl_IncrRefCount(list);

for (i = 0; i < array_length; i++) {
VALUE element = rb_ary_entry(array, i);
Tcl_Obj *string = Tcl_NewStringObj(RSTRING(rb_value_to_s(element))->ptr, -1);
Tcl_Obj *string = Tcl_NewStringObj(RSTRING_PTR(rb_value_to_s(element)), -1);

Tcl_IncrRefCount(string);
Tcl_ListObjAppendElement(tcl_interp->interp, list, string);
Expand Down
Binary file added tcl-0.0.1.gem
Binary file not shown.
Binary file added tcl-0.0.2.gem
Binary file not shown.
77 changes: 39 additions & 38 deletions tcl.gemspec
Original file line number Diff line number Diff line change
Expand Up @@ -4,58 +4,59 @@
# -*- encoding: utf-8 -*-

Gem::Specification.new do |s|
s.name = %q{tcl}
s.version = "0.0.1"
s.name = "tcl"
s.version = "0.0.2"

s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
s.authors = ["Sam Stephenson"]
s.authors = ["Sam Stephenson", "John Mair (banisterfiend)"]
s.date = %q{2009-12-01}
s.description = %q{A minimal Ruby interface to libtcl}
s.email = %q{sstephenson@gmail.com}
s.extensions = ["ext/tcl_ruby/extconf.rb"]
s.extra_rdoc_files = [
"LICENSE",
"README.rdoc",
"TODO"
]
"LICENSE",
"README.rdoc",
"TODO"
]
s.files = [
".gitignore",
"LICENSE",
"README.rdoc",
"Rakefile",
"TODO",
"VERSION",
"ext/tcl_ruby/extconf.rb",
"ext/tcl_ruby/tcl_ruby.c",
"lib/.gitignore",
"lib/tcl.rb",
"lib/tcl/interp.rb",
"lib/tcl/interp_helper.rb",
"lib/tcl/proc.rb",
"lib/tcl/var.rb",
"script/console",
"tcl.gemspec",
"test/fixtures/test.tcl",
"test/helper.rb",
"test/interp_receive_test.rb",
"test/interp_test.rb",
"test/proc_test.rb",
"test/test_helper.rb",
"test/var_test.rb"
]
".gitignore",
"LICENSE",
"README.rdoc",
"Rakefile",
"TODO",
"VERSION",
"ext/tcl_ruby/extconf.rb",
"ext/tcl_ruby/tcl_ruby.c",
"ext/tcl_ruby/compat.h",
"lib/.gitignore",
"lib/tcl.rb",
"lib/tcl/interp.rb",
"lib/tcl/interp_helper.rb",
"lib/tcl/proc.rb",
"lib/tcl/var.rb",
"script/console",
"tcl.gemspec",
"test/fixtures/test.tcl",
"test/helper.rb",
"test/interp_receive_test.rb",
"test/interp_test.rb",
"test/proc_test.rb",
"test/test_helper.rb",
"test/var_test.rb"
]
s.homepage = %q{http://github.com/sstephenson/ruby-tcl}
s.rdoc_options = ["--charset=UTF-8"]
s.require_paths = ["lib"]
s.rubygems_version = %q{1.3.5}
s.summary = %q{Tcl bindings for Ruby}
s.test_files = [
"test/helper.rb",
"test/interp_receive_test.rb",
"test/interp_test.rb",
"test/proc_test.rb",
"test/test_helper.rb",
"test/var_test.rb"
]
"test/helper.rb",
"test/interp_receive_test.rb",
"test/interp_test.rb",
"test/proc_test.rb",
"test/test_helper.rb",
"test/var_test.rb"
]

if s.respond_to? :specification_version then
current_version = Gem::Specification::CURRENT_SPECIFICATION_VERSION
Expand Down