Skip to content

Instantly share code, notes, and snippets.

@methodmissing
Created January 16, 2010 02:58
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save methodmissing/278618 to your computer and use it in GitHub Desktop.
Save methodmissing/278618 to your computer and use it in GitHub Desktop.
GC.enable_stats
class S
def initialize(a)
@a = a
end
end
ITER = 5
Benchmark.bmbm do |results|
results.report("GC") do
ITER.times do
1.upto(10000) {
tmp = [0,1,2,3,4,5,6,7,8,9]
}
tmp = nil
l=nil
100000.times {
l = S.new(l)
}
GC.start
l = []
100000.times {
l.push([l])
}
GC.start
100000.times {
Time.now
}
100000.times {|i|
i.to_s
}
end
end
end
puts "\n\nGC allocations #{GC.num_allocations}, GC collections #{GC.collections}, GC time #{GC.time}"
methodmissing:rubyenterpriseedition187-248 lourens$ gcc -v
Using built-in specs.
Target: x86_64-apple-darwin10
Configured with: ../gcc-4.4.1/configure --prefix=/opt/local --build=x86_64-apple-darwin10 --enable-languages=c,c++,objc,obj-c++,java,fortran --libdir=/opt/local/lib/gcc44 --includedir=/opt/local/include/gcc44 --infodir=/opt/local/share/info --mandir=/opt/local/share/man --with-local-prefix=/opt/local --with-system-zlib --disable-nls --program-suffix=-mp-4.4 --with-gxx-include-dir=/opt/local/include/gcc44/c++/ --with-gmp=/opt/local --with-mpfr=/opt/local
Thread model: posix
gcc version 4.4.1 (GCC)
diff --git a/configure.in b/configure.in
index 090077e..59cb074 100644
--- a/configure.in
+++ b/configure.in
@@ -670,6 +670,15 @@ if test "$use_setreuid" = yes; then
AC_DEFINE(USE_SETREUID)
AC_DEFINE(USE_SETREGID)
fi
+
+AC_ARG_ENABLE(threaded-dispatch,
+ [ --enable-threaded-dispatch use threaded dispatch for rb_eval],
+ [use_threaded_dispatch=$enableval])
+if test "$use_threaded_dispatch" = yes; then
+ AC_DEFINE(USE_THREADED_DISPATCH)
+ XCFLAGS="$XCFLAGS -fno-gcse"
+fi
+
AC_STRUCT_TIMEZONE
AC_CACHE_CHECK(for struct tm.tm_gmtoff, rb_cv_member_struct_tm_tm_gmtoff,
[AC_TRY_COMPILE([#include <time.h>],
diff --git a/gc.c b/gc.c
index 8c1c6d6..dda1835 100644
--- a/gc.c
+++ b/gc.c
@@ -1395,12 +1395,219 @@ rb_gc_mark(ptr)
}
}
+#ifdef THREADED_DISPATCH
+#define NODE_MARK_TABLE \
+static const int node_mark_table[104] = { \
+ &&NODE_MARK_NODE_UNDEF - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_OP_ASGN1 - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_POSTEXE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_CDECL - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_OP_ASGN1 - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_CLASS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_ARGS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_CLASS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_UNDEF - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_ARGS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_ARGS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_CLASS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_CLASS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_SVALUE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_SVALUE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_POSTEXE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_POSTEXE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_NONE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_CLASS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_CLASS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_OP_ASGN1 - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_ARGS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_ARGS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_UNDEF - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_CLASS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_UNDEF - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_UNDEF - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_UNDEF - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_UNDEF - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_UNDEF - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_CDECL - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_UNDEF - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_UNDEF - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_OP_ASGN1 - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_NONE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_ARGS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_ARGS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_OP_ASGN1 - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_NEWLINE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_POSTEXE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_NEWLINE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_POSTEXE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_OP_ASGN1 - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_POSTEXE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_SVALUE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_SVALUE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_SVALUE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_POSTEXE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_POSTEXE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_POSTEXE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_POSTEXE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_NONE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_POSTEXE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_POSTEXE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_POSTEXE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_SVALUE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_ARGS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_ARGS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_SVALUE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_SVALUE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_OP_ASGN1 - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_SVALUE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_OP_ASGN1 - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_UNDEF - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_OP_ASGN1 - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_OP_ASGN1 - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_ARGS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_NONE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_NONE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_SVALUE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_SVALUE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_SVALUE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_POSTEXE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_CDECL - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_NEWLINE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_OP_ASGN1 - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_ARGS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_ARGS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_UNDEF - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_CLASS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_ARGS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_ARGS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_SVALUE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_UNDEF - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_CLASS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_ARGS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_ARGS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_ARGS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_ARGS - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_POSTEXE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_POSTEXE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_POSTEXE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_POSTEXE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_POSTEXE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_SVALUE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_NEWLINE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_POSTEXE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_ALLOCA - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_NONE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_NONE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_NONE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_NONE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_NONE - &&NODE_MARK_NODE_UNDEF, \
+ &&NODE_MARK_NODE_NONE - &&NODE_MARK_NODE_UNDEF \
+};
+#define OBJ_MARK_TABLE \
+static const int obj_mark_table[64] = { \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_T_OBJECT - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_T_MODULE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_T_MODULE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_T_MODULE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_T_BLKTAG - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_T_STRING - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_T_BLKTAG - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_T_ARRAY - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_T_HASH - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_T_STRUCT - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_T_BLKTAG - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_T_BLKTAG - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_T_DATA - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_T_MATCH - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_T_BLKTAG - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_T_VARMAP - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_T_SCOPE - &&OBJ_MARK_NONE, \
+ &&OBJ_MARK_NONE - &&OBJ_MARK_NONE, \
+};
+#define MARK_NODE(nd) NODE_MARK_##nd:
+#define MARK_NODE_ALIAS(nd)
+#define MARK_NODE_BEGIN goto *(&&NODE_MARK_NODE_UNDEF + node_mark_table[nd_type(obj)]);
+#define MARK_NODE_DEFAULT NODE_MARK_NODE_NONE:
+#define MARK_NODE_END
+#define MARK_NEXT goto again;
+#define MARK_OBJ_BEGIN goto *(&&OBJ_MARK_NONE + obj_mark_table[obj->as.basic.flags & T_MASK]);
+#define MARK_OBJ(obj) OBJ_MARK_##obj:
+#define MARK_OBJ_ALIAS(obj)
+#define BREAK return;
+#define MARK_OBJ_DEFAULT OBJ_MARK_NONE:
+#define MARK_OBJ_END
+#else
+#define NODE_MARK_TABLE
+#define MARK_NODE_BEGIN switch (nd_type(obj)) {
+#define MARK_NODE(nd) case (nd):
+#define MARK_NODE_ALIAS(nd) case (nd):
+#define MARK_NODE_DEFAULT default:
+#define MARK_NODE_END }
+#define OBJ_MARK_TABLE
+#define MARK_NEXT goto again;
+#define MARK_OBJ_BEGIN switch (obj->as.basic.flags & T_MASK) {
+#define MARK_OBJ(obj) case (obj):
+#define MARK_OBJ_ALIAS(obj) case (obj):
+#define BREAK break;
+#define MARK_OBJ_DEFAULT default:
+#define MARK_OBJ_END }
+#endif
+
static void
gc_mark_children(ptr)
VALUE ptr;
{
RVALUE *obj = RANY(ptr);
+ NODE_MARK_TABLE;
+ OBJ_MARK_TABLE;
+
goto marking; /* skip */
again:
@@ -1423,126 +1630,126 @@ gc_mark_children(ptr)
case T_NODE:
mark_source_filename(obj->as.node.nd_file);
- switch (nd_type(obj)) {
- case NODE_IF: /* 1,2,3 */
- case NODE_FOR:
- case NODE_ITER:
- case NODE_CREF:
- case NODE_WHEN:
- case NODE_MASGN:
- case NODE_RESCUE:
- case NODE_RESBODY:
- case NODE_CLASS:
+ MARK_NODE_BEGIN;
+ MARK_NODE_ALIAS(NODE_IF); /* 1,2,3 */
+ MARK_NODE_ALIAS(NODE_FOR);
+ MARK_NODE_ALIAS(NODE_ITER);
+ MARK_NODE_ALIAS(NODE_CREF);
+ MARK_NODE_ALIAS(NODE_WHEN);
+ MARK_NODE_ALIAS(NODE_MASGN);
+ MARK_NODE_ALIAS(NODE_RESCUE);
+ MARK_NODE_ALIAS(NODE_RESBODY);
+ MARK_NODE(NODE_CLASS);
gc_mark((VALUE)obj->as.node.u2.node);
/* fall through */
- case NODE_BLOCK: /* 1,3 */
- case NODE_ARRAY:
- case NODE_DSTR:
- case NODE_DXSTR:
- case NODE_DREGX:
- case NODE_DREGX_ONCE:
- case NODE_FBODY:
- case NODE_ENSURE:
- case NODE_CALL:
- case NODE_DEFS:
- case NODE_OP_ASGN1:
+ MARK_NODE_ALIAS(NODE_BLOCK); /* 1,3 */
+ MARK_NODE_ALIAS(NODE_ARRAY);
+ MARK_NODE_ALIAS(NODE_DSTR);
+ MARK_NODE_ALIAS(NODE_DXSTR);
+ MARK_NODE_ALIAS(NODE_DREGX);
+ MARK_NODE_ALIAS(NODE_DREGX_ONCE);
+ MARK_NODE_ALIAS(NODE_FBODY);
+ MARK_NODE_ALIAS(NODE_ENSURE);
+ MARK_NODE_ALIAS(NODE_CALL);
+ MARK_NODE_ALIAS(NODE_DEFS);
+ MARK_NODE(NODE_OP_ASGN1);
gc_mark((VALUE)obj->as.node.u1.node);
/* fall through */
- case NODE_SUPER: /* 3 */
- case NODE_FCALL:
- case NODE_DEFN:
- case NODE_NEWLINE:
+ MARK_NODE_ALIAS(NODE_SUPER); /* 3 */
+ MARK_NODE_ALIAS(NODE_FCALL);
+ MARK_NODE_ALIAS(NODE_DEFN);
+ MARK_NODE(NODE_NEWLINE);
ptr = (VALUE)obj->as.node.u3.node;
- goto again;
-
- case NODE_WHILE: /* 1,2 */
- case NODE_UNTIL:
- case NODE_AND:
- case NODE_OR:
- case NODE_CASE:
- case NODE_SCLASS:
- case NODE_DOT2:
- case NODE_DOT3:
- case NODE_FLIP2:
- case NODE_FLIP3:
- case NODE_MATCH2:
- case NODE_MATCH3:
- case NODE_OP_ASGN_OR:
- case NODE_OP_ASGN_AND:
- case NODE_MODULE:
- case NODE_ALIAS:
- case NODE_VALIAS:
- case NODE_ARGS:
+ MARK_NEXT;
+
+ MARK_NODE_ALIAS(NODE_WHILE); /* 1,2 */
+ MARK_NODE_ALIAS(NODE_UNTIL);
+ MARK_NODE_ALIAS(NODE_AND);
+ MARK_NODE_ALIAS(NODE_OR);
+ MARK_NODE_ALIAS(NODE_CASE);
+ MARK_NODE_ALIAS(NODE_SCLASS);
+ MARK_NODE_ALIAS(NODE_DOT2);
+ MARK_NODE_ALIAS(NODE_DOT3);
+ MARK_NODE_ALIAS(NODE_FLIP2);
+ MARK_NODE_ALIAS(NODE_FLIP3);
+ MARK_NODE_ALIAS(NODE_MATCH2);
+ MARK_NODE_ALIAS(NODE_MATCH3);
+ MARK_NODE_ALIAS(NODE_OP_ASGN_OR);
+ MARK_NODE_ALIAS(NODE_OP_ASGN_AND);
+ MARK_NODE_ALIAS(NODE_MODULE);
+ MARK_NODE_ALIAS(NODE_ALIAS);
+ MARK_NODE_ALIAS(NODE_VALIAS);
+ MARK_NODE(NODE_ARGS);
gc_mark((VALUE)obj->as.node.u1.node);
/* fall through */
- case NODE_METHOD: /* 2 */
- case NODE_NOT:
- case NODE_GASGN:
- case NODE_LASGN:
- case NODE_DASGN:
- case NODE_DASGN_CURR:
- case NODE_IASGN:
- case NODE_CVDECL:
- case NODE_CVASGN:
- case NODE_COLON3:
- case NODE_OPT_N:
- case NODE_EVSTR:
- case NODE_UNDEF:
+ MARK_NODE_ALIAS(NODE_METHOD); /* 2 */
+ MARK_NODE_ALIAS(NODE_NOT);
+ MARK_NODE_ALIAS(NODE_GASGN);
+ MARK_NODE_ALIAS(NODE_LASGN);
+ MARK_NODE_ALIAS(NODE_DASGN);
+ MARK_NODE_ALIAS(NODE_DASGN_CURR);
+ MARK_NODE_ALIAS(NODE_IASGN);
+ MARK_NODE_ALIAS(NODE_CVDECL);
+ MARK_NODE_ALIAS(NODE_CVASGN);
+ MARK_NODE_ALIAS(NODE_COLON3);
+ MARK_NODE_ALIAS(NODE_OPT_N);
+ MARK_NODE_ALIAS(NODE_EVSTR);
+ MARK_NODE(NODE_UNDEF);
ptr = (VALUE)obj->as.node.u2.node;
- goto again;
-
- case NODE_HASH: /* 1 */
- case NODE_LIT:
- case NODE_STR:
- case NODE_XSTR:
- case NODE_DEFINED:
- case NODE_MATCH:
- case NODE_RETURN:
- case NODE_BREAK:
- case NODE_NEXT:
- case NODE_YIELD:
- case NODE_COLON2:
- case NODE_SPLAT:
- case NODE_TO_ARY:
- case NODE_SVALUE:
+ MARK_NEXT;
+
+ MARK_NODE_ALIAS(NODE_HASH); /* 1 */
+ MARK_NODE_ALIAS(NODE_LIT);
+ MARK_NODE_ALIAS(NODE_STR);
+ MARK_NODE_ALIAS(NODE_XSTR);
+ MARK_NODE_ALIAS(NODE_DEFINED);
+ MARK_NODE_ALIAS(NODE_MATCH);
+ MARK_NODE_ALIAS(NODE_RETURN);
+ MARK_NODE_ALIAS(NODE_BREAK);
+ MARK_NODE_ALIAS(NODE_NEXT);
+ MARK_NODE_ALIAS(NODE_YIELD);
+ MARK_NODE_ALIAS(NODE_COLON2);
+ MARK_NODE_ALIAS(NODE_SPLAT);
+ MARK_NODE_ALIAS(NODE_TO_ARY);
+ MARK_NODE(NODE_SVALUE);
ptr = (VALUE)obj->as.node.u1.node;
- goto again;
+ MARK_NEXT;
- case NODE_SCOPE: /* 2,3 */
- case NODE_BLOCK_PASS:
- case NODE_CDECL:
+ MARK_NODE_ALIAS(NODE_SCOPE); /* 2,3 */
+ MARK_NODE_ALIAS(NODE_BLOCK_PASS);
+ MARK_NODE(NODE_CDECL);
gc_mark((VALUE)obj->as.node.u3.node);
ptr = (VALUE)obj->as.node.u2.node;
- goto again;
-
- case NODE_ZARRAY: /* - */
- case NODE_ZSUPER:
- case NODE_CFUNC:
- case NODE_VCALL:
- case NODE_GVAR:
- case NODE_LVAR:
- case NODE_DVAR:
- case NODE_IVAR:
- case NODE_CVAR:
- case NODE_NTH_REF:
- case NODE_BACK_REF:
- case NODE_REDO:
- case NODE_RETRY:
- case NODE_SELF:
- case NODE_NIL:
- case NODE_TRUE:
- case NODE_FALSE:
- case NODE_ATTRSET:
- case NODE_BLOCK_ARG:
- case NODE_POSTEXE:
- break;
- case NODE_ALLOCA:
+ MARK_NEXT;
+
+ MARK_NODE_ALIAS(NODE_ZARRAY); /* - */
+ MARK_NODE_ALIAS(NODE_ZSUPER);
+ MARK_NODE_ALIAS(NODE_CFUNC);
+ MARK_NODE_ALIAS(NODE_VCALL);
+ MARK_NODE_ALIAS(NODE_GVAR);
+ MARK_NODE_ALIAS(NODE_LVAR);
+ MARK_NODE_ALIAS(NODE_DVAR);
+ MARK_NODE_ALIAS(NODE_IVAR);
+ MARK_NODE_ALIAS(NODE_CVAR);
+ MARK_NODE_ALIAS(NODE_NTH_REF);
+ MARK_NODE_ALIAS(NODE_BACK_REF);
+ MARK_NODE_ALIAS(NODE_REDO);
+ MARK_NODE_ALIAS(NODE_RETRY);
+ MARK_NODE_ALIAS(NODE_SELF);
+ MARK_NODE_ALIAS(NODE_NIL);
+ MARK_NODE_ALIAS(NODE_TRUE);
+ MARK_NODE_ALIAS(NODE_FALSE);
+ MARK_NODE_ALIAS(NODE_ATTRSET);
+ MARK_NODE_ALIAS(NODE_BLOCK_ARG);
+ MARK_NODE(NODE_POSTEXE);
+ BREAK;
+ MARK_NODE(NODE_ALLOCA);
mark_locations_array((VALUE*)obj->as.node.u1.value,
obj->as.node.u3.cnt);
ptr = (VALUE)obj->as.node.u2.node;
- goto again;
+ MARK_NEXT;
- default: /* unlisted NODE */
+ MARK_NODE_DEFAULT; /* unlisted NODE */
if (is_pointer_to_heap(obj->as.node.u1.node)) {
gc_mark((VALUE)obj->as.node.u1.node);
}
@@ -1551,26 +1758,26 @@ gc_mark_children(ptr)
}
if (is_pointer_to_heap(obj->as.node.u3.node)) {
ptr = (VALUE)obj->as.node.u3.node;
- goto again;
+ MARK_NEXT;
}
- }
+ MARK_NODE_END;
return; /* no need to mark class. */
}
gc_mark(obj->as.basic.klass);
- switch (obj->as.basic.flags & T_MASK) {
- case T_ICLASS:
- case T_CLASS:
- case T_MODULE:
+ MARK_OBJ_BEGIN;
+ MARK_OBJ_ALIAS(T_ICLASS);
+ MARK_OBJ_ALIAS(T_CLASS);
+ MARK_OBJ(T_MODULE);
mark_tbl(obj->as.klass.m_tbl);
mark_tbl(obj->as.klass.iv_tbl);
ptr = obj->as.klass.super;
- goto again;
+ MARK_NEXT;
- case T_ARRAY:
+ MARK_OBJ(T_ARRAY);
if (FL_TEST(obj, ELTS_SHARED)) {
ptr = obj->as.array.aux.shared;
- goto again;
+ MARK_NEXT;
}
else {
VALUE *ptr = obj->as.array.ptr;
@@ -1579,49 +1786,49 @@ gc_mark_children(ptr)
gc_mark(*ptr++);
}
}
- break;
+ BREAK;
- case T_HASH:
+ MARK_OBJ(T_HASH);
mark_hash(obj->as.hash.tbl);
ptr = obj->as.hash.ifnone;
- goto again;
+ MARK_NEXT;
- case T_STRING:
+ MARK_OBJ(T_STRING);
#define STR_ASSOC FL_USER3 /* copied from string.c */
if (FL_TEST(obj, ELTS_SHARED|STR_ASSOC)) {
ptr = obj->as.string.aux.shared;
- goto again;
+ MARK_NEXT;
}
- break;
+ BREAK;
- case T_DATA:
+ MARK_OBJ(T_DATA);
if (obj->as.data.dmark) (*obj->as.data.dmark)(DATA_PTR(obj));
- break;
+ BREAK;
- case T_OBJECT:
+ MARK_OBJ(T_OBJECT);
mark_tbl(obj->as.object.iv_tbl);
- break;
+ BREAK;
- case T_FILE:
- case T_REGEXP:
- case T_FLOAT:
- case T_BIGNUM:
- case T_BLKTAG:
- break;
+ MARK_OBJ_ALIAS(T_FILE);
+ MARK_OBJ_ALIAS(T_REGEXP);
+ MARK_OBJ_ALIAS(T_FLOAT);
+ MARK_OBJ_ALIAS(T_BIGNUM);
+ MARK_OBJ(T_BLKTAG);
+ BREAK;
- case T_MATCH:
+ MARK_OBJ(T_MATCH);
if (obj->as.match.str) {
ptr = obj->as.match.str;
- goto again;
+ MARK_NEXT;
}
- break;
+ BREAK;
- case T_VARMAP:
+ MARK_OBJ(T_VARMAP);
gc_mark(obj->as.varmap.val);
ptr = (VALUE)obj->as.varmap.next;
- goto again;
+ MARK_NEXT;
- case T_SCOPE:
+ MARK_OBJ(T_SCOPE);
if (obj->as.scope.local_vars && (obj->as.scope.flags & SCOPE_MALLOC)) {
int n = obj->as.scope.local_tbl[0]+1;
VALUE *vars = &obj->as.scope.local_vars[-1];
@@ -1630,22 +1837,22 @@ gc_mark_children(ptr)
gc_mark(*vars++);
}
}
- break;
+ BREAK;
- case T_STRUCT:
+ MARK_OBJ(T_STRUCT);
{
VALUE *ptr = obj->as.rstruct.ptr;
VALUE *pend = ptr + obj->as.rstruct.len;
while (ptr < pend)
gc_mark(*ptr++);
}
- break;
+ BREAK;
- default:
+ MARK_OBJ_DEFAULT;
rb_bug("rb_gc_mark(): unknown data type 0x%lx(0x%lx) %s",
obj->as.basic.flags & T_MASK, obj,
is_pointer_to_heap(obj) ? "corrupted object" : "non object");
- }
+ MARK_OBJ_END;
}
static int obj_free _((VALUE));
diff --git a/ruby.h b/ruby.h
index 4d003a8..8cc114e 100644
--- a/ruby.h
+++ b/ruby.h
@@ -53,6 +53,10 @@ extern "C" {
#include <stddef.h>
#include <stdio.h>
+#if (defined(__GNUC__) || defined (__SUNPRO_C)) && defined(USE_THREADED_DISPATCH)
+#define THREADED_DISPATCH
+#endif
+
/* need to include <ctype.h> to use these macros */
#ifndef ISPRINT
#define ISASCII(c) isascii((int)(unsigned char)(c))
methodmissing:rubyenterpriseedition187-248 lourens$ ./ruby -Ilib gc_bench.rb
Rehearsal --------------------------------------
GC 1.920000 0.110000 2.030000 ( 2.037465)
----------------------------- total: 2.030000sec
user system total real
GC 1.890000 0.090000 1.980000 ( 1.986451)
GC allocations 6100164, GC collections 76, GC time 1285786
methodmissing:rubyenterpriseedition187-248 lourens$ ./ruby -Ilib gc_bench.rb
Rehearsal --------------------------------------
GC 1.920000 0.100000 2.020000 ( 2.034541)
----------------------------- total: 2.020000sec
user system total real
GC 1.890000 0.100000 1.990000 ( 1.983895)
GC allocations 6100164, GC collections 76, GC time 1285663
methodmissing:rubyenterpriseedition187-248 lourens$ ./ruby -Ilib gc_bench.rb
Rehearsal --------------------------------------
GC 1.940000 0.110000 2.050000 ( 2.083771)
----------------------------- total: 2.050000sec
user system total real
GC 1.880000 0.100000 1.980000 ( 1.983069)
GC allocations 6100164, GC collections 76, GC time 1298704
methodmissing:rubyenterpriseedition187-248 lourens$ ./ruby -Ilib gc_bench.rb
Rehearsal --------------------------------------
GC 1.930000 0.110000 2.040000 ( 2.046354)
----------------------------- total: 2.040000sec
user system total real
GC 1.880000 0.090000 1.970000 ( 1.984479)
GC allocations 6100164, GC collections 76, GC time 1291290
methodmissing:rubyenterpriseedition187-248 lourens$ ./ruby -Ilib gc_bench.rb
Rehearsal --------------------------------------
GC 1.920000 0.100000 2.020000 ( 2.034159)
----------------------------- total: 2.020000sec
user system total real
GC 1.890000 0.100000 1.990000 ( 1.986119)
GC allocations 6100164, GC collections 76, GC time 1283219
methodmissing:rubyenterpriseedition187-248 lourens$ ./ruby -Ilib gc_bench.rb
Rehearsal --------------------------------------
GC 1.930000 0.110000 2.040000 ( 2.042077)
----------------------------- total: 2.040000sec
user system total real
GC 1.890000 0.100000 1.990000 ( 2.000116)
GC allocations 6100164, GC collections 76, GC time 1295255
methodmissing:rubyenterpriseedition187-248 lourens$ ./ruby -Ilib gc_bench.rb
Rehearsal --------------------------------------
GC 1.910000 0.100000 2.010000 ( 2.020122)
----------------------------- total: 2.010000sec
user system total real
GC 1.890000 0.100000 1.990000 ( 1.984007)
GC allocations 6100164, GC collections 76, GC time 1281519
methodmissing:rubyenterpriseedition187-248 lourens$ ./ruby -Ilib gc_bench.rb
Rehearsal --------------------------------------
GC 1.930000 0.110000 2.040000 ( 2.046567)
----------------------------- total: 2.040000sec
user system total real
GC 1.880000 0.100000 1.980000 ( 1.983995)
GC allocations 6100164, GC collections 76, GC time 1293953
methodmissing:rubyenterpriseedition187-248 lourens$ ./ruby -Ilib gc_bench.rb
Rehearsal --------------------------------------
GC 1.890000 0.100000 1.990000 ( 2.002766)
----------------------------- total: 1.990000sec
user system total real
GC 1.880000 0.100000 1.980000 ( 1.978341)
GC allocations 6100164, GC collections 104, GC time 1350239
methodmissing:rubyenterpriseedition187-248 lourens$
methodmissing:rubyenterpriseedition187-248 lourens$ ./ruby -Ilib gc_bench.rb
Rehearsal --------------------------------------
GC 1.880000 0.100000 1.980000 ( 1.994420)
----------------------------- total: 1.980000sec
user system total real
GC 1.870000 0.100000 1.970000 ( 1.975207)
GC allocations 6100164, GC collections 104, GC time 1347193
methodmissing:rubyenterpriseedition187-248 lourens$ ./ruby -Ilib gc_bench.rb
Rehearsal --------------------------------------
GC 1.880000 0.100000 1.980000 ( 1.994267)
----------------------------- total: 1.980000sec
user system total real
GC 1.880000 0.100000 1.980000 ( 1.976741)
GC allocations 6100164, GC collections 104, GC time 1349683
methodmissing:rubyenterpriseedition187-248 lourens$ ./ruby -Ilib gc_bench.rb
Rehearsal --------------------------------------
GC 1.900000 0.120000 2.020000 ( 2.034585)
----------------------------- total: 2.020000sec
user system total real
GC 1.880000 0.100000 1.980000 ( 2.012661)
GC allocations 6100164, GC collections 104, GC time 1374953
methodmissing:rubyenterpriseedition187-248 lourens$ ./ruby -Ilib gc_bench.rb
Rehearsal --------------------------------------
GC 1.880000 0.100000 1.980000 ( 1.990765)
----------------------------- total: 1.980000sec
user system total real
GC 1.880000 0.110000 1.990000 ( 1.985680)
GC allocations 6100164, GC collections 104, GC time 1350603
methodmissing:rubyenterpriseedition187-248 lourens$ ./ruby -Ilib gc_bench.rb
Rehearsal --------------------------------------
GC 1.890000 0.100000 1.990000 ( 1.994218)
----------------------------- total: 1.990000sec
user system total real
GC 1.870000 0.100000 1.970000 ( 1.975965)
GC allocations 6100164, GC collections 104, GC time 1348079
methodmissing:rubyenterpriseedition187-248 lourens$ ./ruby -Ilib gc_bench.rb
Rehearsal --------------------------------------
GC 1.890000 0.100000 1.990000 ( 1.997950)
----------------------------- total: 1.990000sec
user system total real
GC 1.870000 0.100000 1.970000 ( 1.975340)
GC allocations 6100164, GC collections 104, GC time 1349620
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment