objspace_helpers 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: c64bb3dba9f6e3592d48191859735a4a982057d4
4
+ data.tar.gz: af65ffc525b86d06a64c0bcd75852512408bee98
5
+ SHA512:
6
+ metadata.gz: 07223b0ee7fe06143270fd91f66f07da4a324e832e57875b4941bd3059eb9e40da01dbae0e127624f21dc0a012c9c6a855cd682e8ece0a7e6b69716d97052621
7
+ data.tar.gz: 31e9b72f8f15653f86b2853965470504b82c9165370315a8ba520b4d98df8360023f0490b4affe5ef74ccad0e39cc88c3f2758dd5f8fd73485c02044006df4cc
data/LICENSE ADDED
@@ -0,0 +1,24 @@
1
+ Copyright (c) 2014, Lukas Fittl <lukas@fittl.com>
2
+ All rights reserved.
3
+
4
+ Redistribution and use in source and binary forms, with or without
5
+ modification, are permitted provided that the following conditions are met:
6
+
7
+ * Redistributions of source code must retain the above copyright notice, this
8
+ list of conditions and the following disclaimer.
9
+
10
+ * Redistributions in binary form must reproduce the above copyright notice,
11
+ this list of conditions and the following disclaimer in the documentation
12
+ and/or other materials provided with the distribution.
13
+
14
+ THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15
+ AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16
+ IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17
+ ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18
+ LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19
+ CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20
+ SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21
+ INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22
+ CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23
+ ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24
+ POSSIBILITY OF SUCH DAMAGE.
data/Rakefile ADDED
@@ -0,0 +1,20 @@
1
+ require "bundler/gem_tasks"
2
+ require "rake/extensiontask"
3
+ require "rspec/core/rake_task"
4
+
5
+ Rake::ExtensionTask.new "objspace_helpers" do |ext|
6
+ ext.lib_dir = "lib/objspace_helpers"
7
+ end
8
+
9
+ RSpec::Core::RakeTask.new
10
+
11
+ task spec: :compile
12
+
13
+ task default: :spec
14
+ task test: :spec
15
+
16
+ task :clean do
17
+ FileUtils.rm_rf File.join(File.dirname(__FILE__), "tmp/")
18
+ FileUtils.rm_f Dir.glob(File.join(File.dirname(__FILE__), "ext/objspace_helpers/*.o"))
19
+ FileUtils.rm_f File.join(File.dirname(__FILE__), "lib/objspace_helpers/objspace_helpers.bundle")
20
+ end
@@ -0,0 +1,5 @@
1
+ require 'mkmf'
2
+
3
+ $objs = ["objspace_info.o", "objspace_helpers.o"]
4
+
5
+ create_makefile 'objspace_helpers/objspace_helpers'
@@ -0,0 +1,60 @@
1
+ #include <objspace_info.h>
2
+
3
+ void Init_objspace_helpers(void);
4
+
5
+ static int
6
+ collect_addresses(void *vstart, void *vend, size_t stride, void *data)
7
+ {
8
+ VALUE v = (VALUE)vstart;
9
+ for (; v != (VALUE)vend; v += stride) {
10
+ if (RBASIC(v)->flags)
11
+ rb_ary_push((VALUE) data, INT2FIX((void *)v));
12
+ }
13
+ return 0;
14
+ }
15
+
16
+ static VALUE oh_dump_addresses(VALUE self)
17
+ {
18
+ VALUE ary = rb_ary_new();
19
+ rb_objspace_each_objects(collect_addresses, (void *)ary);
20
+ return ary;
21
+ }
22
+
23
+ static VALUE oh_addresses_to_info(VALUE self, VALUE ary)
24
+ {
25
+ VALUE hash, obj_addr, info_hash;
26
+ long i;
27
+
28
+ hash = rb_hash_new();
29
+
30
+ for (i = 0; i < RARRAY_LEN(ary); i += 1) {
31
+ obj_addr = rb_ary_entry(ary, i);
32
+ info_hash = rb_hash_new();
33
+ objspace_info(FIX2PTR(obj_addr), info_hash);
34
+ rb_hash_aset(hash, obj_addr, info_hash);
35
+ }
36
+
37
+ return hash;
38
+ }
39
+
40
+ static VALUE oh_address_of_obj(VALUE self, VALUE obj)
41
+ {
42
+ return PTR2FIX(obj);
43
+ }
44
+
45
+ static VALUE oh_obj_for_address(VALUE self, VALUE address)
46
+ {
47
+ return FIX2PTR(address);
48
+ }
49
+
50
+ void Init_objspace_helpers(void)
51
+ {
52
+ VALUE cObjspaceHelpers;
53
+
54
+ cObjspaceHelpers = rb_const_get(rb_cObject, rb_intern("ObjspaceHelpers"));
55
+
56
+ rb_define_singleton_method(cObjspaceHelpers, "_dump_addresses", oh_dump_addresses, 0);
57
+ rb_define_singleton_method(cObjspaceHelpers, "_addresses_to_info", oh_addresses_to_info, 1);
58
+ rb_define_singleton_method(cObjspaceHelpers, "_address_of_obj", oh_address_of_obj, 1);
59
+ rb_define_singleton_method(cObjspaceHelpers, "_obj_for_address", oh_obj_for_address, 1);
60
+ }
@@ -0,0 +1,10 @@
1
+ #ifndef RUBY_OBJSPACE_HELPERS
2
+ #define RUBY_OBJSPACE_HELPERS
3
+
4
+ #include <ruby.h>
5
+ #include <ruby_private/gc.h>
6
+
7
+ #define PTR2FIX(v) INT2FIX((void *)v)
8
+ #define FIX2PTR(v) ((VALUE)NUM2SIZET(v))
9
+
10
+ #endif
@@ -0,0 +1,175 @@
1
+ #include <objspace_info.h>
2
+
3
+ static inline const char *
4
+ obj_type(VALUE obj)
5
+ {
6
+ switch (BUILTIN_TYPE(obj)) {
7
+ #define CASE_TYPE(type) case T_##type: return #type; break
8
+ CASE_TYPE(NONE);
9
+ CASE_TYPE(NIL);
10
+ CASE_TYPE(OBJECT);
11
+ CASE_TYPE(CLASS);
12
+ CASE_TYPE(ICLASS);
13
+ CASE_TYPE(MODULE);
14
+ CASE_TYPE(FLOAT);
15
+ CASE_TYPE(STRING);
16
+ CASE_TYPE(REGEXP);
17
+ CASE_TYPE(ARRAY);
18
+ CASE_TYPE(HASH);
19
+ CASE_TYPE(STRUCT);
20
+ CASE_TYPE(BIGNUM);
21
+ CASE_TYPE(FILE);
22
+ CASE_TYPE(FIXNUM);
23
+ CASE_TYPE(TRUE);
24
+ CASE_TYPE(FALSE);
25
+ CASE_TYPE(DATA);
26
+ CASE_TYPE(MATCH);
27
+ CASE_TYPE(SYMBOL);
28
+ CASE_TYPE(RATIONAL);
29
+ CASE_TYPE(COMPLEX);
30
+ CASE_TYPE(UNDEF);
31
+ CASE_TYPE(NODE);
32
+ CASE_TYPE(ZOMBIE);
33
+ #undef CASE_TYPE
34
+ }
35
+ return "UNKNOWN";
36
+ }
37
+
38
+ static void
39
+ reachable_object_i(VALUE ref, void *data)
40
+ {
41
+ rb_ary_push((VALUE)data, PTR2FIX(ref));
42
+ }
43
+
44
+ #define HASH_SET(k,v) rb_hash_aset(target_hash, rb_str_new2(k), v)
45
+ #define HASH_SET_PTR(k,v) HASH_SET(k,INT2FIX((void *)v))
46
+ #define HASH_SET_INT(k,v) HASH_SET(k,INT2FIX(v))
47
+ #define HASH_SET_UINT(k,v) HASH_SET(k,UINT2NUM(v))
48
+ #define HASH_SET_ULONG(k,v) HASH_SET(k,ULONG2NUM(v))
49
+ #define HASH_SET_STR(k,v) HASH_SET(k,rb_str_new2(v))
50
+ #define HASH_SET_TRUE(k) HASH_SET(k,Qtrue)
51
+
52
+ void
53
+ objspace_info(VALUE obj, VALUE target_hash)
54
+ {
55
+ size_t memsize;
56
+ struct allocation_info *ainfo;
57
+ rb_io_t *fptr;
58
+ ID flags[RB_OBJ_GC_FLAGS_MAX];
59
+ size_t n, i;
60
+ VALUE obj_klass, references;
61
+
62
+ obj_klass = BUILTIN_TYPE(obj) == T_NODE ? 0 : RBASIC_CLASS(obj);
63
+ references = rb_ary_new();
64
+
65
+ if (obj == target_hash)
66
+ return;
67
+
68
+ HASH_SET_STR("type", obj_type(obj));
69
+
70
+ if (obj_klass)
71
+ HASH_SET_PTR("class", obj_klass);
72
+ if (rb_obj_frozen_p(obj))
73
+ HASH_SET_TRUE("frozen");
74
+
75
+ switch (BUILTIN_TYPE(obj)) {
76
+ case T_NODE:
77
+ HASH_SET_STR("node_type", ruby_node_name(nd_type(obj)));
78
+ break;
79
+
80
+ case T_STRING:
81
+ if (STR_EMBED_P(obj))
82
+ HASH_SET_TRUE("embedded");
83
+ if (STR_ASSOC_P(obj))
84
+ HASH_SET_TRUE("associated");
85
+ if (is_broken_string(obj))
86
+ HASH_SET_TRUE("broken");
87
+ if (FL_TEST(obj, RSTRING_FSTR))
88
+ HASH_SET_TRUE("fstring");
89
+ if (STR_SHARED_P(obj))
90
+ HASH_SET_TRUE("shared");
91
+ else {
92
+ HASH_SET_INT("bytesize", RSTRING_LEN(obj));
93
+
94
+ if (!STR_EMBED_P(obj) && !STR_NOCAPA_P(obj) && (long)rb_str_capacity(obj) != RSTRING_LEN(obj))
95
+ HASH_SET_INT("capacity", rb_str_capacity(obj));
96
+
97
+ if (is_ascii_string(obj))
98
+ HASH_SET("value", obj);
99
+ }
100
+
101
+ if (!ENCODING_IS_ASCII8BIT(obj))
102
+ HASH_SET_STR("encoding", rb_enc_name(rb_enc_from_index(ENCODING_GET(obj))));
103
+
104
+ break;
105
+
106
+ case T_HASH:
107
+ HASH_SET_INT("size", RHASH_SIZE(obj));
108
+
109
+ if (FL_TEST(obj, HASH_PROC_DEFAULT))
110
+ HASH_SET_PTR("default", RHASH_IFNONE(obj));
111
+ break;
112
+
113
+ case T_ARRAY:
114
+ HASH_SET_INT("length", RARRAY_LEN(obj));
115
+
116
+ if (RARRAY_LEN(obj) > 0 && FL_TEST(obj, ELTS_SHARED))
117
+ HASH_SET_TRUE("shared");
118
+ if (RARRAY_LEN(obj) > 0 && FL_TEST(obj, RARRAY_EMBED_FLAG))
119
+ HASH_SET_TRUE("embedded");
120
+
121
+ break;
122
+
123
+ case T_CLASS:
124
+ case T_MODULE:
125
+ if (obj_klass)
126
+ HASH_SET_STR("name", rb_class2name(obj));
127
+ break;
128
+
129
+ case T_DATA:
130
+ if (RTYPEDDATA_P(obj))
131
+ HASH_SET_STR("struct", RTYPEDDATA_TYPE(obj)->wrap_struct_name);
132
+ break;
133
+
134
+ case T_FLOAT:
135
+ HASH_SET("value", obj);
136
+ break;
137
+
138
+ case T_OBJECT:
139
+ HASH_SET_INT("ivars", ROBJECT_NUMIV(obj));
140
+ break;
141
+
142
+ case T_FILE:
143
+ fptr = RFILE(obj)->fptr;
144
+ if (fptr)
145
+ HASH_SET_INT("fd", fptr->fd);
146
+ break;
147
+
148
+ case T_ZOMBIE:
149
+ return;
150
+ }
151
+
152
+ rb_objspace_reachable_objects_from(obj, reachable_object_i, (void*)references);
153
+ rb_ary_delete(references, PTR2FIX(obj_klass));
154
+ HASH_SET("references", references);
155
+
156
+ if ((ainfo = objspace_lookup_allocation_info(obj))) {
157
+ HASH_SET_STR("file", ainfo->path);
158
+ HASH_SET_ULONG("line", ainfo->line);
159
+ HASH_SET_UINT("generation", ainfo->generation);
160
+
161
+ if (RTEST(ainfo->mid))
162
+ HASH_SET_STR("method", rb_id2name(SYM2ID(ainfo->mid)));
163
+ }
164
+
165
+ if ((memsize = rb_obj_memsize_of(obj)) > 0)
166
+ HASH_SET_UINT("memsize", memsize);
167
+
168
+ if ((n = rb_obj_gc_flags(obj, flags, sizeof(flags))) > 0) {
169
+ VALUE flags_hash = rb_hash_new();
170
+ for (i=0; i<n; i++) {
171
+ rb_hash_aset(flags_hash, rb_str_new2(rb_id2name(flags[i])), Qtrue);
172
+ }
173
+ HASH_SET("flags", flags_hash);
174
+ }
175
+ }
@@ -0,0 +1,15 @@
1
+ #ifndef RUBY_OBJSPACE_INFO
2
+ #define RUBY_OBJSPACE_INFO
3
+
4
+ #include <ruby.h>
5
+ #include <ruby/io.h>
6
+
7
+ #include <ruby_private/internal_defs.h>
8
+ #include <ruby_private/objspace.h>
9
+
10
+ #include <objspace_helpers.h>
11
+
12
+ void
13
+ objspace_info(VALUE obj, VALUE target_hash);
14
+
15
+ #endif
@@ -0,0 +1,107 @@
1
+
2
+ #ifndef RUBY_GC_H
3
+ #define RUBY_GC_H 1
4
+
5
+ #if defined(__x86_64__) && !defined(_ILP32) && defined(__GNUC__) && !defined(__native_client__)
6
+ #define SET_MACHINE_STACK_END(p) __asm__ __volatile__ ("movq\t%%rsp, %0" : "=r" (*(p)))
7
+ #elif defined(__i386) && defined(__GNUC__) && !defined(__native_client__)
8
+ #define SET_MACHINE_STACK_END(p) __asm__ __volatile__ ("movl\t%%esp, %0" : "=r" (*(p)))
9
+ #else
10
+ NOINLINE(void rb_gc_set_stack_end(VALUE **stack_end_p));
11
+ #define SET_MACHINE_STACK_END(p) rb_gc_set_stack_end(p)
12
+ #define USE_CONSERVATIVE_STACK_END
13
+ #endif
14
+
15
+ /* for GC debug */
16
+
17
+ #ifndef RUBY_MARK_FREE_DEBUG
18
+ #define RUBY_MARK_FREE_DEBUG 0
19
+ #endif
20
+
21
+ #if RUBY_MARK_FREE_DEBUG
22
+ extern int ruby_gc_debug_indent;
23
+
24
+ static inline void
25
+ rb_gc_debug_indent(void)
26
+ {
27
+ printf("%*s", ruby_gc_debug_indent, "");
28
+ }
29
+
30
+ static inline void
31
+ rb_gc_debug_body(const char *mode, const char *msg, int st, void *ptr)
32
+ {
33
+ if (st == 0) {
34
+ ruby_gc_debug_indent--;
35
+ }
36
+ rb_gc_debug_indent();
37
+ printf("%s: %s %s (%p)\n", mode, st ? "->" : "<-", msg, ptr);
38
+
39
+ if (st) {
40
+ ruby_gc_debug_indent++;
41
+ }
42
+
43
+ fflush(stdout);
44
+ }
45
+
46
+ #define RUBY_MARK_ENTER(msg) rb_gc_debug_body("mark", (msg), 1, ptr)
47
+ #define RUBY_MARK_LEAVE(msg) rb_gc_debug_body("mark", (msg), 0, ptr)
48
+ #define RUBY_FREE_ENTER(msg) rb_gc_debug_body("free", (msg), 1, ptr)
49
+ #define RUBY_FREE_LEAVE(msg) rb_gc_debug_body("free", (msg), 0, ptr)
50
+ #define RUBY_GC_INFO rb_gc_debug_indent(); printf
51
+
52
+ #else
53
+ #define RUBY_MARK_ENTER(msg)
54
+ #define RUBY_MARK_LEAVE(msg)
55
+ #define RUBY_FREE_ENTER(msg)
56
+ #define RUBY_FREE_LEAVE(msg)
57
+ #define RUBY_GC_INFO if(0)printf
58
+ #endif
59
+
60
+ #define RUBY_MARK_UNLESS_NULL(ptr) if(RTEST(ptr)){rb_gc_mark(ptr);}
61
+ #define RUBY_FREE_UNLESS_NULL(ptr) if(ptr){ruby_xfree(ptr);(ptr)=NULL;}
62
+
63
+ #if STACK_GROW_DIRECTION > 0
64
+ # define STACK_UPPER(x, a, b) (a)
65
+ #elif STACK_GROW_DIRECTION < 0
66
+ # define STACK_UPPER(x, a, b) (b)
67
+ #else
68
+ RUBY_EXTERN int ruby_stack_grow_direction;
69
+ int ruby_get_stack_grow_direction(volatile VALUE *addr);
70
+ # define stack_growup_p(x) ( \
71
+ (ruby_stack_grow_direction ? \
72
+ ruby_stack_grow_direction : \
73
+ ruby_get_stack_grow_direction(x)) > 0)
74
+ # define STACK_UPPER(x, a, b) (stack_growup_p(x) ? (a) : (b))
75
+ #endif
76
+
77
+ #if STACK_GROW_DIRECTION
78
+ #define STACK_GROW_DIR_DETECTION
79
+ #define STACK_DIR_UPPER(a,b) STACK_UPPER(0, (a), (b))
80
+ #else
81
+ #define STACK_GROW_DIR_DETECTION VALUE stack_grow_dir_detection
82
+ #define STACK_DIR_UPPER(a,b) STACK_UPPER(&stack_grow_dir_detection, (a), (b))
83
+ #endif
84
+ #define IS_STACK_DIR_UPPER() STACK_DIR_UPPER(1,0)
85
+
86
+ RUBY_SYMBOL_EXPORT_BEGIN
87
+
88
+ /* exports for objspace module */
89
+ size_t rb_objspace_data_type_memsize(VALUE obj);
90
+ void rb_objspace_reachable_objects_from(VALUE obj, void (func)(VALUE, void *), void *data);
91
+ void rb_objspace_reachable_objects_from_root(void (func)(const char *category, VALUE, void *), void *data);
92
+ int rb_objspace_markable_object_p(VALUE obj);
93
+ int rb_objspace_internal_object_p(VALUE obj);
94
+ int rb_objspace_marked_object_p(VALUE obj);
95
+ int rb_objspace_garbage_object_p(VALUE obj);
96
+
97
+ void rb_objspace_each_objects(
98
+ int (*callback)(void *start, void *end, size_t stride, void *data),
99
+ void *data);
100
+
101
+ void rb_objspace_each_objects_without_setup(
102
+ int (*callback)(void *, void *, size_t, void *),
103
+ void *data);
104
+
105
+ RUBY_SYMBOL_EXPORT_END
106
+
107
+ #endif /* RUBY_GC_H */
@@ -0,0 +1,87 @@
1
+ /* internal.h */
2
+
3
+ #define STR_NOEMBED FL_USER1
4
+ #define STR_SHARED FL_USER2 /* = ELTS_SHARED */
5
+ #define STR_ASSOC FL_USER3
6
+ #define STR_SHARED_P(s) FL_ALL((s), STR_NOEMBED|ELTS_SHARED)
7
+ #define STR_ASSOC_P(s) FL_ALL((s), STR_NOEMBED|STR_ASSOC)
8
+ #define STR_NOCAPA (STR_NOEMBED|ELTS_SHARED|STR_ASSOC)
9
+ #define STR_NOCAPA_P(s) (FL_TEST((s),STR_NOEMBED) && FL_ANY((s),ELTS_SHARED|STR_ASSOC))
10
+ #define STR_EMBED_P(str) (!FL_TEST((str), STR_NOEMBED))
11
+ #define is_ascii_string(str) (rb_enc_str_coderange(str) == ENC_CODERANGE_7BIT)
12
+ #define is_broken_string(str) (rb_enc_str_coderange(str) == ENC_CODERANGE_BROKEN)
13
+
14
+ #define HASH_DELETED FL_USER1
15
+ #define HASH_PROC_DEFAULT FL_USER2
16
+
17
+ size_t rb_obj_memsize_of(VALUE);
18
+ #define RB_OBJ_GC_FLAGS_MAX 5
19
+ size_t rb_obj_gc_flags(VALUE, ID[], size_t);
20
+ void rb_gc_mark_values(long n, const VALUE *values);
21
+
22
+
23
+ /* vm_core.h */
24
+
25
+ const char *ruby_node_name(int node);
26
+
27
+ /* debug.h */
28
+
29
+ VALUE rb_tracepoint_new(VALUE target_thread_not_supported_yet, rb_event_flag_t events, void (*func)(VALUE, void *), void *data);
30
+ VALUE rb_tracepoint_enable(VALUE tpval);
31
+ VALUE rb_tracepoint_disable(VALUE tpval);
32
+ VALUE rb_tracepoint_enabled_p(VALUE tpval);
33
+
34
+ typedef struct rb_trace_arg_struct rb_trace_arg_t;
35
+ rb_trace_arg_t *rb_tracearg_from_tracepoint(VALUE tpval);
36
+
37
+ rb_event_flag_t rb_tracearg_event_flag(rb_trace_arg_t *trace_arg);
38
+ VALUE rb_tracearg_event(rb_trace_arg_t *trace_arg);
39
+ VALUE rb_tracearg_lineno(rb_trace_arg_t *trace_arg);
40
+ VALUE rb_tracearg_path(rb_trace_arg_t *trace_arg);
41
+ VALUE rb_tracearg_method_id(rb_trace_arg_t *trace_arg);
42
+ VALUE rb_tracearg_defined_class(rb_trace_arg_t *trace_arg);
43
+ VALUE rb_tracearg_binding(rb_trace_arg_t *trace_arg);
44
+ VALUE rb_tracearg_self(rb_trace_arg_t *trace_arg);
45
+ VALUE rb_tracearg_return_value(rb_trace_arg_t *trace_arg);
46
+ VALUE rb_tracearg_raised_exception(rb_trace_arg_t *trace_arg);
47
+ VALUE rb_tracearg_object(rb_trace_arg_t *trace_arg);
48
+
49
+ /* node.h */
50
+
51
+ typedef struct RNode {
52
+ VALUE flags;
53
+ VALUE nd_reserved; /* ex nd_file */
54
+ union {
55
+ struct RNode *node;
56
+ ID id;
57
+ VALUE value;
58
+ VALUE (*cfunc)(ANYARGS);
59
+ ID *tbl;
60
+ } u1;
61
+ union {
62
+ struct RNode *node;
63
+ ID id;
64
+ long argc;
65
+ VALUE value;
66
+ } u2;
67
+ union {
68
+ struct RNode *node;
69
+ ID id;
70
+ long state;
71
+ struct rb_global_entry *entry;
72
+ struct rb_args_info *args;
73
+ long cnt;
74
+ VALUE value;
75
+ } u3;
76
+ } NODE;
77
+
78
+ #define RNODE(obj) (R_CAST(RNode)(obj))
79
+
80
+ #define NODE_FL_NEWLINE (((VALUE)1)<<7)
81
+ #define NODE_FL_CREF_PUSHED_BY_EVAL (((VALUE)1)<<15)
82
+ #define NODE_FL_CREF_OMOD_SHARED (((VALUE)1)<<16)
83
+
84
+ #define NODE_TYPESHIFT 8
85
+ #define NODE_TYPEMASK (((VALUE)0x7f)<<NODE_TYPESHIFT)
86
+
87
+ #define nd_type(n) ((int) (((RNODE(n))->flags & NODE_TYPEMASK)>>NODE_TYPESHIFT))
@@ -0,0 +1,15 @@
1
+ /* object_tracing.c */
2
+ struct allocation_info {
3
+ /* all of information don't need marking. */
4
+ int living;
5
+ VALUE flags;
6
+ VALUE klass;
7
+
8
+ /* allocation info */
9
+ const char *path;
10
+ unsigned long line;
11
+ const char *class_path;
12
+ VALUE mid;
13
+ size_t generation;
14
+ };
15
+ extern struct allocation_info *objspace_lookup_allocation_info(VALUE obj);
@@ -0,0 +1,28 @@
1
+ class ObjspaceHelpers
2
+ def self.dump_all_addresses
3
+ _dump_addresses
4
+ end
5
+
6
+ def self.info_for_address(addresses)
7
+ _addresses_to_info(addresses)
8
+ end
9
+
10
+ def self.info_for_obj(obj)
11
+ _addresses_to_info([address_of(obj)]).values.first
12
+ end
13
+
14
+ def self.obj_for(address)
15
+ _obj_for_address(address)
16
+ end
17
+
18
+ def self.address_of(obj)
19
+ _address_of_obj(obj)
20
+ end
21
+
22
+ def self.diff(&block)
23
+ objs_before = dump_all_addresses
24
+ block.call
25
+ objs_after = dump_all_addresses
26
+ objs_after - objs_before - [address_of(objs_after)]
27
+ end
28
+ end
@@ -0,0 +1,3 @@
1
+ class ObjspaceHelpers
2
+ VERSION = '0.0.1'
3
+ end
@@ -0,0 +1,6 @@
1
+ require 'objspace'
2
+
3
+ require 'objspace_helpers/version'
4
+ require 'objspace_helpers/objspace_helpers'
5
+
6
+ require 'objspace_helpers/helpers'
metadata ADDED
@@ -0,0 +1,99 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: objspace_helpers
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ platform: ruby
6
+ authors:
7
+ - Lukas Fittl
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2014-11-24 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: rake-compiler
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: '0'
20
+ type: :development
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: '0'
27
+ - !ruby/object:Gem::Dependency
28
+ name: rspec
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - "~>"
32
+ - !ruby/object:Gem::Version
33
+ version: '3.0'
34
+ type: :development
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - "~>"
39
+ - !ruby/object:Gem::Version
40
+ version: '3.0'
41
+ - !ruby/object:Gem::Dependency
42
+ name: json
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - "~>"
46
+ - !ruby/object:Gem::Version
47
+ version: '1.8'
48
+ type: :runtime
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - "~>"
53
+ - !ruby/object:Gem::Version
54
+ version: '1.8'
55
+ description: Diff the heap to find leaks & get other ObjectSpace info more easily.
56
+ email: lukas@fittl.com
57
+ executables: []
58
+ extensions:
59
+ - ext/objspace_helpers/extconf.rb
60
+ extra_rdoc_files: []
61
+ files:
62
+ - LICENSE
63
+ - Rakefile
64
+ - ext/objspace_helpers/extconf.rb
65
+ - ext/objspace_helpers/objspace_helpers.c
66
+ - ext/objspace_helpers/objspace_helpers.h
67
+ - ext/objspace_helpers/objspace_info.c
68
+ - ext/objspace_helpers/objspace_info.h
69
+ - ext/objspace_helpers/ruby_private/gc.h
70
+ - ext/objspace_helpers/ruby_private/internal_defs.h
71
+ - ext/objspace_helpers/ruby_private/objspace.h
72
+ - lib/objspace_helpers.rb
73
+ - lib/objspace_helpers/helpers.rb
74
+ - lib/objspace_helpers/version.rb
75
+ homepage: http://github.com/lfittl/objspace_helpers
76
+ licenses:
77
+ - BSD-2-Clause
78
+ metadata: {}
79
+ post_install_message:
80
+ rdoc_options: []
81
+ require_paths:
82
+ - lib
83
+ required_ruby_version: !ruby/object:Gem::Requirement
84
+ requirements:
85
+ - - ">="
86
+ - !ruby/object:Gem::Version
87
+ version: '0'
88
+ required_rubygems_version: !ruby/object:Gem::Requirement
89
+ requirements:
90
+ - - ">="
91
+ - !ruby/object:Gem::Version
92
+ version: '0'
93
+ requirements: []
94
+ rubyforge_project:
95
+ rubygems_version: 2.2.2
96
+ signing_key:
97
+ specification_version: 4
98
+ summary: Helper library to work with ObjectSpace in MRI Ruby 2.1+
99
+ test_files: []