Ruby 2.1.5p273(2014-11-13revision48405)

- Main Page
- Modules
- Data Structures
- Files

- File List
- Globals

object_tracing.c
Go to the documentation of this file.
1 /**********************************************************************
2
3 object_tracing.c - Object Tracing mechanism/ObjectSpace extender for MRI.
4
5 $Author$
6 created at: Mon May 27 16:27:44 2013
7
8 NOTE: This extension library is not expected to exist except C Ruby.
9 NOTE: This feature is an example usage of internal event tracing APIs.
10
11 All the files in this distribution are covered under the Ruby's
12 license (see the file COPYING).
13
14 **********************************************************************/
15
16 #include "ruby/ruby.h"
17 #include "ruby/debug.h"
18 #include "objspace.h"
19 #include "internal.h"
20
21 struct traceobj_arg {
22 int running;
23 int keep_remains;
24 VALUE newobj_trace;
25 VALUE freeobj_trace;
26 st_table *object_table; /* obj (VALUE) -> allocation_info */
27 st_table *str_table; /* cstr -> refcount */
28 struct traceobj_arg *prev_traceobj_arg;
29 };
30
31 static const char *
32 make_unique_str(st_table *tbl, const char *str, long len)
33 {
34 if (!str) {
35 return NULL;
36 }
37 else {
38 st_data_t n;
39 char *result;
40
41 if (st_lookup(tbl, (st_data_t)str, &n)) {
42 st_insert(tbl, (st_data_t)str, n+1);
43 st_get_key(tbl, (st_data_t)str, (st_data_t *)&result);
44 }
45 else {
46 result = (char *)ruby_xmalloc(len+1);
47 strncpy(result, str, len);
48 result[len] = 0;
49 st_add_direct(tbl, (st_data_t)result, 1);
50 }
51 return result;
52 }
53 }
54
55 static void
56 delete_unique_str(st_table *tbl, const char *str)
57 {
58 if (str) {
59 st_data_t n;
60
61 st_lookup(tbl, (st_data_t)str, &n);
62 if (n == 1) {
63 st_delete(tbl, (st_data_t *)&str, 0);
64 ruby_xfree((char *)str);
65 }
66 else {
67 st_insert(tbl, (st_data_t)str, n-1);
68 }
69 }
70 }
71
72 static void
73 newobj_i(VALUE tpval, void *data)
74 {
75 struct traceobj_arg *arg = (struct traceobj_arg *)data;
76 rb_trace_arg_t *tparg = rb_tracearg_from_tracepoint(tpval);
77 VALUE obj = rb_tracearg_object(tparg);
78 VALUE path = rb_tracearg_path(tparg);
79 VALUE line = rb_tracearg_lineno(tparg);
80 VALUE mid = rb_tracearg_method_id(tparg);
81 VALUE klass = rb_tracearg_defined_class(tparg);
82 struct allocation_info *info;
83 const char *path_cstr = RTEST(path) ? make_unique_str(arg->str_table, RSTRING_PTR(path), RSTRING_LEN(path)) : 0;
84 VALUE class_path = (RTEST(klass) && !OBJ_FROZEN(klass)) ? rb_class_path_cached(klass) : Qnil;
85 const char *class_path_cstr = RTEST(class_path) ? make_unique_str(arg->str_table, RSTRING_PTR(class_path), RSTRING_LEN(class_path)) : 0;
86
87 if (st_lookup(arg->object_table, (st_data_t)obj, (st_data_t *)&info)) {
88 if (arg->keep_remains) {
89 if (info->living) {
90 /* do nothing. there is possibility to keep living if FREEOBJ events while suppressing tracing */
91 }
92 }
93 /* reuse info */
94 delete_unique_str(arg->str_table, info->path);
95 delete_unique_str(arg->str_table, info->class_path);
96 }
97 else {
98 info = (struct allocation_info *)ruby_xmalloc(sizeof(struct allocation_info));
99 }
100 info->living = 1;
101 info->flags = RBASIC(obj)->flags;
102 info->klass = RBASIC_CLASS(obj);
103
104 info->path = path_cstr;
105 info->line = NUM2INT(line);
106 info->mid = mid;
107 info->class_path = class_path_cstr;
108 info->generation = rb_gc_count();
109 st_insert(arg->object_table, (st_data_t)obj, (st_data_t)info);
110 }
111
112 static void
113 freeobj_i(VALUE tpval, void *data)
114 {
115 struct traceobj_arg *arg = (struct traceobj_arg *)data;
116 rb_trace_arg_t *tparg = rb_tracearg_from_tracepoint(tpval);
117 VALUE obj = rb_tracearg_object(tparg);
118 struct allocation_info *info;
119
120 if (st_lookup(arg->object_table, (st_data_t)obj, (st_data_t *)&info)) {
121 if (arg->keep_remains) {
122 info->living = 0;
123 }
124 else {
125 st_delete(arg->object_table, (st_data_t *)&obj, (st_data_t *)&info);
126 delete_unique_str(arg->str_table, info->path);
127 delete_unique_str(arg->str_table, info->class_path);
128 ruby_xfree(info);
129 }
130 }
131 }
132
133 static int
134 free_keys_i(st_data_t key, st_data_t value, void *data)
135 {
136 ruby_xfree((void *)key);
137 return ST_CONTINUE;
138 }
139
140 static int
141 free_values_i(st_data_t key, st_data_t value, void *data)
142 {
143 ruby_xfree((void *)value);
144 return ST_CONTINUE;
145 }
146
147 static struct traceobj_arg *tmp_trace_arg; /* TODO: Do not use global variables */
148 static int tmp_keep_remains; /* TODO: Do not use global variables */
149
150 static struct traceobj_arg *
151 get_traceobj_arg(void)
152 {
153 if (tmp_trace_arg == 0) {
154 tmp_trace_arg = ALLOC_N(struct traceobj_arg, 1);
155 tmp_trace_arg->running = 0;
156 tmp_trace_arg->keep_remains = tmp_keep_remains;
157 tmp_trace_arg->newobj_trace = 0;
158 tmp_trace_arg->freeobj_trace = 0;
159 tmp_trace_arg->object_table = st_init_numtable();
160 tmp_trace_arg->str_table = st_init_strtable();
161 }
162 return tmp_trace_arg;
163 }
164
165 /*
166 * call-seq: trace_object_allocations_start
167 *
168 * Starts tracing object allocations.
169 *
170 */
171 static VALUE
172 trace_object_allocations_start(VALUE self)
173 {
174 struct traceobj_arg *arg = get_traceobj_arg();
175
176 if (arg->running++ > 0) {
177 /* do nothing */
178 }
179 else {
180 if (arg->newobj_trace == 0) {
181 arg->newobj_trace = rb_tracepoint_new(0, RUBY_INTERNAL_EVENT_NEWOBJ, newobj_i, arg);
182 arg->freeobj_trace = rb_tracepoint_new(0, RUBY_INTERNAL_EVENT_FREEOBJ, freeobj_i, arg);
183 }
184 rb_tracepoint_enable(arg->newobj_trace);
185 rb_tracepoint_enable(arg->freeobj_trace);
186 }
187
188 return Qnil;
189 }
190
191 /*
192 * call-seq: trace_object_allocations_stop
193 *
194 * Stop tracing object allocations.
195 *
196 * Note that if ::trace_object_allocations_start is called n-times, then
197 * tracing will stop after calling ::trace_object_allocations_stop n-times.
198 *
199 */
200 static VALUE
201 trace_object_allocations_stop(VALUE self)
202 {
203 struct traceobj_arg *arg = get_traceobj_arg();
204
205 if (arg->running > 0) {
206 arg->running--;
207 }
208
209 if (arg->running == 0) {
210 rb_tracepoint_disable(arg->newobj_trace);
211 rb_tracepoint_disable(arg->freeobj_trace);
212 arg->newobj_trace = 0;
213 arg->freeobj_trace = 0;
214 }
215
216 return Qnil;
217 }
218
219 /*
220 * call-seq: trace_object_allocations_clear
221 *
222 * Clear recorded tracing information.
223 *
224 */
225 static VALUE
226 trace_object_allocations_clear(VALUE self)
227 {
228 struct traceobj_arg *arg = get_traceobj_arg();
229
230 /* clear tables */
231 st_foreach(arg->object_table, free_values_i, 0);
232 st_clear(arg->object_table);
233 st_foreach(arg->str_table, free_keys_i, 0);
234 st_clear(arg->str_table);
235
236 /* do not touch TracePoints */
237
238 return Qnil;
239 }
240
241 /*
242 * call-seq: trace_object_allocations { block }
243 *
244 * Starts tracing object allocations from the ObjectSpace extension module.
245 *
246 * For example:
247 *
248 * require 'objspace'
249 *
250 * class C
251 * include ObjectSpace
252 *
253 * def foo
254 * trace_object_allocations do
255 * obj = Object.new
256 * p "#{allocation_sourcefile(obj)}:#{allocation_sourceline(obj)}"
257 * end
258 * end
259 * end
260 *
261 * C.new.foo #=> "objtrace.rb:8"
262 *
263 * This example has included the ObjectSpace module to make it easier to read,
264 * but you can also use the ::trace_object_allocations notation (recommended).
265 *
266 * Note that this feature introduces a huge performance decrease and huge
267 * memory consumption.
268 */
269 static VALUE
270 trace_object_allocations(VALUE self)
271 {
272 trace_object_allocations_start(self);
273 return rb_ensure(rb_yield, Qnil, trace_object_allocations_stop, self);
274 }
275
276 int rb_bug_reporter_add(void (*func)(FILE *, void *), void *data);
277 static int object_allocations_reporter_registered = 0;
278
279 static int
280 object_allocations_reporter_i(st_data_t key, st_data_t val, st_data_t ptr)
281 {
282 FILE *out = (FILE *)ptr;
283 VALUE obj = (VALUE)key;
284 struct allocation_info *info = (struct allocation_info *)val;
285
286 fprintf(out, "-- %p (%s F: %p, ", (void *)obj, info->living ? "live" : "dead", (void *)info->flags);
287 if (info->class_path) fprintf(out, "C: %s", info->class_path);
288 else fprintf(out, "C: %p", (void *)info->klass);
289 fprintf(out, "@%s:%lu", info->path ? info->path : "", info->line);
290 if (!NIL_P(info->mid)) fprintf(out, " (%s)", rb_id2name(SYM2ID(info->mid)));
291 fprintf(out, ")\n");
292
293 return ST_CONTINUE;
294 }
295
296 static void
297 object_allocations_reporter(FILE *out, void *ptr)
298 {
299 fprintf(out, "== object_allocations_reporter: START\n");
300 if (tmp_trace_arg) {
301 st_foreach(tmp_trace_arg->object_table, object_allocations_reporter_i, (st_data_t)out);
302 }
303 fprintf(out, "== object_allocations_reporter: END\n");
304 }
305
306 static VALUE
307 trace_object_allocations_debug_start(VALUE self)
308 {
309 tmp_keep_remains = 1;
310 if (object_allocations_reporter_registered == 0) {
311 object_allocations_reporter_registered = 1;
312 rb_bug_reporter_add(object_allocations_reporter, 0);
313 }
314
315 return trace_object_allocations_start(self);
316 }
317
318 static struct allocation_info *
319 lookup_allocation_info(VALUE obj)
320 {
321 if (tmp_trace_arg) {
322 struct allocation_info *info;
323 if (st_lookup(tmp_trace_arg->object_table, obj, (st_data_t *)&info)) {
324 return info;
325 }
326 }
327 return NULL;
328 }
329
330 struct allocation_info *
331 objspace_lookup_allocation_info(VALUE obj)
332 {
333 return lookup_allocation_info(obj);
334 }
335
336 /*
337 * call-seq: allocation_sourcefile(object) -> string
338 *
339 * Returns the source file origin from the given +object+.
340 *
341 * See ::trace_object_allocations for more information and examples.
342 */
343 static VALUE
344 allocation_sourcefile(VALUE self, VALUE obj)
345 {
346 struct allocation_info *info = lookup_allocation_info(obj);
347
348 if (info && info->path) {
349 return rb_str_new2(info->path);
350 }
351 else {
352 return Qnil;
353 }
354 }
355
356 /*
357 * call-seq: allocation_sourceline(object) -> string
358 *
359 * Returns the original line from source for from the given +object+.
360 *
361 * See ::trace_object_allocations for more information and examples.
362 */
363 static VALUE
364 allocation_sourceline(VALUE self, VALUE obj)
365 {
366 struct allocation_info *info = lookup_allocation_info(obj);
367
368 if (info) {
369 return INT2FIX(info->line);
370 }
371 else {
372 return Qnil;
373 }
374 }
375
376 /*
377 * call-seq: allocation_class_path(object) -> string
378 *
379 * Returns the class for the given +object+.
380 *
381 * class A
382 * def foo
383 * ObjectSpace::trace_object_allocations do
384 * obj = Object.new
385 * p "#{ObjectSpace::allocation_class_path(obj)}"
386 * end
387 * end
388 * end
389 *
390 * A.new.foo #=> "Class"
391 *
392 * See ::trace_object_allocations for more information and examples.
393 */
394 static VALUE
395 allocation_class_path(VALUE self, VALUE obj)
396 {
397 struct allocation_info *info = lookup_allocation_info(obj);
398
399 if (info && info->class_path) {
400 return rb_str_new2(info->class_path);
401 }
402 else {
403 return Qnil;
404 }
405 }
406
407 /*
408 * call-seq: allocation_method_id(object) -> string
409 *
410 * Returns the method identifier for the given +object+.
411 *
412 * class A
413 * include ObjectSpace
414 *
415 * def foo
416 * trace_object_allocations do
417 * obj = Object.new
418 * p "#{allocation_class_path(obj)}##{allocation_method_id(obj)}"
419 * end
420 * end
421 * end
422 *
423 * A.new.foo #=> "Class#new"
424 *
425 * See ::trace_object_allocations for more information and examples.
426 */
427 static VALUE
428 allocation_method_id(VALUE self, VALUE obj)
429 {
430 struct allocation_info *info = lookup_allocation_info(obj);
431 if (info) {
432 return info->mid;
433 }
434 else {
435 return Qnil;
436 }
437 }
438
439 /*
440 * call-seq: allocation_generation(object) -> Fixnum
441 *
442 * Returns garbage collector generation for the given +object+.
443 *
444 * class B
445 * include ObjectSpace
446 *
447 * def foo
448 * trace_object_allocations do
449 * obj = Object.new
450 * p "Generation is #{allocation_generation(obj)}"
451 * end
452 * end
453 * end
454 *
455 * B.new.foo #=> "Generation is 3"
456 *
457 * See ::trace_object_allocations for more information and examples.
458 */
459 static VALUE
460 allocation_generation(VALUE self, VALUE obj)
461 {
462 struct allocation_info *info = lookup_allocation_info(obj);
463 if (info) {
464 return SIZET2NUM(info->generation);
465 }
466 else {
467 return Qnil;
468 }
469 }
470
471 void
472 Init_object_tracing(VALUE rb_mObjSpace)
473 {
474 #if 0
475 rb_mObjSpace = rb_define_module("ObjectSpace"); /* let rdoc know */
476 #endif
477
478 rb_define_module_function(rb_mObjSpace, "trace_object_allocations", trace_object_allocations, 0);
479 rb_define_module_function(rb_mObjSpace, "trace_object_allocations_start", trace_object_allocations_start, 0);
480 rb_define_module_function(rb_mObjSpace, "trace_object_allocations_stop", trace_object_allocations_stop, 0);
481 rb_define_module_function(rb_mObjSpace, "trace_object_allocations_clear", trace_object_allocations_clear, 0);
482
483 rb_define_module_function(rb_mObjSpace, "trace_object_allocations_debug_start", trace_object_allocations_debug_start, 0);
484
485 rb_define_module_function(rb_mObjSpace, "allocation_sourcefile", allocation_sourcefile, 1);
486 rb_define_module_function(rb_mObjSpace, "allocation_sourceline", allocation_sourceline, 1);
487 rb_define_module_function(rb_mObjSpace, "allocation_class_path", allocation_class_path, 1);
488 rb_define_module_function(rb_mObjSpace, "allocation_method_id", allocation_method_id, 1);
489 rb_define_module_function(rb_mObjSpace, "allocation_generation", allocation_generation, 1);
490 }
traceobj_arg::object_table
st_table * object_table
Definition: object_tracing.c:26
trace_object_allocations
static VALUE trace_object_allocations(VALUE self)
Definition: object_tracing.c:270
st_table
Definition: st.h:69
NUM2INT
#define NUM2INT(x)
Definition: ruby.h:630
ruby.h
debug.h
st_insert
int st_insert(st_table *, st_data_t, st_data_t)
ST_CONTINUE
Definition: st.h:100
SYM2ID
#define SYM2ID(x)
Definition: ruby.h:356
allocation_info::living
int living
Definition: objspace.h:7
st_get_key
int st_get_key(st_table *, st_data_t, st_data_t *)
allocation_sourceline
static VALUE allocation_sourceline(VALUE self, VALUE obj)
Definition: object_tracing.c:364
st_init_strtable
st_table * st_init_strtable(void)
Definition: st.c:284
rb_gc_count
size_t rb_gc_count(void)
Definition: gc.c:5219
allocation_info::klass
VALUE klass
Definition: objspace.h:9
traceobj_arg::str_table
st_table * str_table
Definition: object_tracing.c:27
trace_object_allocations_stop
static VALUE trace_object_allocations_stop(VALUE self)
Definition: object_tracing.c:201
free_keys_i
static int free_keys_i(st_data_t key, st_data_t value, void *data)
Definition: object_tracing.c:134
st_data_t
RUBY_SYMBOL_EXPORT_BEGIN typedef unsigned long st_data_t
Definition: st.h:20
__sFILE
Definition: vsnprintf.c:175
allocation_info::generation
size_t generation
Definition: objspace.h:16
traceobj_arg::prev_traceobj_arg
struct traceobj_arg * prev_traceobj_arg
Definition: object_tracing.c:28
st_lookup
int st_lookup(st_table *, st_data_t, st_data_t *)
ALLOC_N
#define ALLOC_N(type, n)
Definition: ruby.h:1333
val
#define val
allocation_method_id
static VALUE allocation_method_id(VALUE self, VALUE obj)
Definition: object_tracing.c:428
free_values_i
static int free_values_i(st_data_t key, st_data_t value, void *data)
Definition: object_tracing.c:141
rb_bug_reporter_add
int rb_bug_reporter_add(void(*func)(FILE *, void *), void *data)
Definition: error.c:282
NIL_P
#define NIL_P(v)
Definition: ruby.h:438
st_add_direct
void st_add_direct(st_table *, st_data_t, st_data_t)
Definition: st.c:629
st_delete
int st_delete(st_table *, st_data_t *, st_data_t *)
allocation_info::line
unsigned long line
Definition: objspace.h:13
tmp_keep_remains
static int tmp_keep_remains
Definition: object_tracing.c:148
Init_object_tracing
void Init_object_tracing(VALUE rb_mObjSpace)
Definition: object_tracing.c:472
OBJ_FROZEN
#define OBJ_FROZEN(x)
Definition: ruby.h:1185
traceobj_arg::keep_remains
int keep_remains
Definition: object_tracing.c:23
allocation_class_path
static VALUE allocation_class_path(VALUE self, VALUE obj)
Definition: object_tracing.c:395
rb_str_new2
#define rb_str_new2
Definition: intern.h:840
tmp_trace_arg
static struct traceobj_arg * tmp_trace_arg
Definition: object_tracing.c:147
get_traceobj_arg
static struct traceobj_arg * get_traceobj_arg(void)
Definition: object_tracing.c:151
rb_tracearg_from_tracepoint
rb_trace_arg_t * rb_tracearg_from_tracepoint(VALUE tpval)
Definition: vm_trace.c:729
RSTRING_LEN
#define RSTRING_LEN(str)
Definition: ruby.h:841
rb_define_module_function
void rb_define_module_function(VALUE module, const char *name, VALUE(*func)(ANYARGS), int argc)
Defines a module function for module.
Definition: class.c:1670
rb_yield
VALUE rb_yield(VALUE)
Definition: vm_eval.c:942
func
SSL_METHOD *(* func)(void)
Definition: ossl_ssl.c:113
rb_tracearg_method_id
VALUE rb_tracearg_method_id(rb_trace_arg_t *trace_arg)
Definition: vm_trace.c:798
delete_unique_str
static void delete_unique_str(st_table *tbl, const char *str)
Definition: object_tracing.c:56
rb_tracearg_defined_class
VALUE rb_tracearg_defined_class(rb_trace_arg_t *trace_arg)
Definition: vm_trace.c:805
ruby_xfree
void ruby_xfree(void *x)
Definition: gc.c:6242
freeobj_i
static void freeobj_i(VALUE tpval, void *data)
Definition: object_tracing.c:113
object_allocations_reporter_i
static int object_allocations_reporter_i(st_data_t key, st_data_t val, st_data_t ptr)
Definition: object_tracing.c:280
internal.h
Qnil
#define Qnil
Definition: ruby.h:427
rb_tracepoint_new
VALUE rb_tracepoint_new(VALUE target_thread_not_supported_yet, rb_event_flag_t events, void(*func)(VALUE, void *), void *data)
Definition: vm_trace.c:1177
VALUE
unsigned long VALUE
Definition: ruby.h:88
result
static VALUE result
Definition: nkf.c:40
RBASIC
#define RBASIC(obj)
Definition: ruby.h:1116
rb_tracearg_lineno
VALUE rb_tracearg_lineno(rb_trace_arg_t *trace_arg)
Definition: vm_trace.c:764
traceobj_arg
Definition: object_tracing.c:21
rb_ensure
VALUE rb_ensure(VALUE(*b_proc)(ANYARGS), VALUE data1, VALUE(*e_proc)(ANYARGS), VALUE data2)
Definition: eval.c:839
allocation_sourcefile
static VALUE allocation_sourcefile(VALUE self, VALUE obj)
Definition: object_tracing.c:344
make_unique_str
static const char * make_unique_str(st_table *tbl, const char *str, long len)
Definition: object_tracing.c:32
st_init_numtable
st_table * st_init_numtable(void)
Definition: st.c:272
ruby_xmalloc
void * ruby_xmalloc(size_t size)
Definition: gc.c:6156
RSTRING_PTR
#define RSTRING_PTR(str)
Definition: ruby.h:845
objspace_lookup_allocation_info
struct allocation_info * objspace_lookup_allocation_info(VALUE obj)
Definition: object_tracing.c:331
object_allocations_reporter_registered
static int object_allocations_reporter_registered
Definition: object_tracing.c:277
rb_tracearg_object
VALUE rb_tracearg_object(rb_trace_arg_t *trace_arg)
Definition: vm_trace.c:862
trace_object_allocations_debug_start
static VALUE trace_object_allocations_debug_start(VALUE self)
Definition: object_tracing.c:307
INT2FIX
#define INT2FIX(i)
Definition: ruby.h:231
lookup_allocation_info
static struct allocation_info * lookup_allocation_info(VALUE obj)
Definition: object_tracing.c:319
allocation_info::mid
VALUE mid
Definition: objspace.h:15
allocation_info::class_path
const char * class_path
Definition: objspace.h:14
RUBY_INTERNAL_EVENT_NEWOBJ
#define RUBY_INTERNAL_EVENT_NEWOBJ
Definition: ruby.h:1732
RUBY_INTERNAL_EVENT_FREEOBJ
#define RUBY_INTERNAL_EVENT_FREEOBJ
Definition: ruby.h:1733
RBASIC_CLASS
#define RBASIC_CLASS(obj)
Definition: ruby.h:759
rb_class_path_cached
VALUE rb_class_path_cached(VALUE)
Definition: variable.c:281
key
uint8_t key[16]
Definition: random.c:1250
rb_trace_arg_struct
Definition: vm_core.h:996
RTEST
#define RTEST(v)
Definition: ruby.h:437
traceobj_arg::newobj_trace
VALUE newobj_trace
Definition: object_tracing.c:24
rb_tracearg_path
VALUE rb_tracearg_path(rb_trace_arg_t *trace_arg)
Definition: vm_trace.c:770
trace_object_allocations_clear
static VALUE trace_object_allocations_clear(VALUE self)
Definition: object_tracing.c:226
rb_id2name
const char * rb_id2name(ID id)
Definition: ripper.c:17230
rb_tracepoint_enable
VALUE rb_tracepoint_enable(VALUE tpval)
Definition: vm_trace.c:1007
allocation_generation
static VALUE allocation_generation(VALUE self, VALUE obj)
Definition: object_tracing.c:460
st_clear
void st_clear(st_table *)
Definition: st.c:308
traceobj_arg::running
int running
Definition: object_tracing.c:22
rb_define_module
VALUE rb_define_module(const char *name)
Definition: class.c:746
object_allocations_reporter
static void object_allocations_reporter(FILE *out, void *ptr)
Definition: object_tracing.c:297
allocation_info
Definition: objspace.h:5
allocation_info::flags
VALUE flags
Definition: objspace.h:8
NULL
#define NULL
Definition: _sdbm.c:103
allocation_info::path
const char * path
Definition: objspace.h:12
st_foreach
int st_foreach(st_table *, int(*)(ANYARGS), st_data_t)
Definition: st.c:1034
rb_tracepoint_disable
VALUE rb_tracepoint_disable(VALUE tpval)
Definition: vm_trace.c:1026
newobj_i
static void newobj_i(VALUE tpval, void *data)
Definition: object_tracing.c:73
SIZET2NUM
#define SIZET2NUM(v)
Definition: ruby.h:262
trace_object_allocations_start
static VALUE trace_object_allocations_start(VALUE self)
Definition: object_tracing.c:172
objspace.h
traceobj_arg::freeobj_trace
VALUE freeobj_trace
Definition: object_tracing.c:25