plain_apm 0.8.3 → 0.8.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/README.md +29 -2
- data/ext/object_tracing/bug18464.rb +8 -0
- data/ext/object_tracing/bug19112.rb +33 -0
- data/ext/object_tracing/extconf.rb +80 -2
- data/ext/object_tracing/object_tracing.c +37 -6
- data/lib/plain_apm/version.rb +1 -1
- metadata +10 -4
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: ff5ddab9e3475ec09d7ef20f6bc5c6ae64ffa0e3ffa946d84def56c33eb41cde
|
4
|
+
data.tar.gz: '085a3004d655b642bbd63b295ce7c41531d2264709820b8f9ab35e31bdfe987d'
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 960c5aad1354d5cc97e43d537807afeac46cdb41db125e9a832447912d2d7b0934041c8e39965bd7f8727fe9d7e4b9600250ce9c687559bfb02347afe90205b4
|
7
|
+
data.tar.gz: 7985afc06387dbfca63c0a69665516ebb3d54cdf88cd4532fba427d03594ab9e0e65c7a4dab08b9e1c1f63d912fb68afad22c62f7348b87d5f09c38ef146c117
|
data/README.md
CHANGED
@@ -13,11 +13,38 @@ gem 'plain_apm'
|
|
13
13
|
|
14
14
|
And then execute:
|
15
15
|
|
16
|
-
|
16
|
+
bundle install
|
17
17
|
|
18
18
|
Or install it yourself as:
|
19
19
|
|
20
|
-
|
20
|
+
gem install plain_apm
|
21
|
+
|
22
|
+
### Ractor and TracePoint issues on Ruby 3.0
|
23
|
+
|
24
|
+
PlainAPM extension to track object allocation on a per-thread basis is
|
25
|
+
built on top of Ruby's TracePoint API.
|
26
|
+
|
27
|
+
However, Rubies 3.0, 3.1, 3.2 and 3.3 as of January 2024 contain bugs
|
28
|
+
which, when Tracepoints are used in together with Ractors, can cause
|
29
|
+
crashes or inconsistent tracing results.
|
30
|
+
|
31
|
+
Build process for the native extension contains checks for presence of
|
32
|
+
these bugs and disables object allocation tracing accordingly.
|
33
|
+
|
34
|
+
If you are sure your app is not using Ractors, you can override this by
|
35
|
+
installing plain_apm with --enable-object-tracing-override flag:
|
36
|
+
|
37
|
+
gem install plain_apm -- --enable-object-tracing-override
|
38
|
+
|
39
|
+
When using bundler, you can configure it to pass this flag to the gem
|
40
|
+
install by running:
|
41
|
+
|
42
|
+
bundle config set --global build.plain_apm --enable-object-tracing-override
|
43
|
+
|
44
|
+
See also:
|
45
|
+
|
46
|
+
- https://bugs.ruby-lang.org/issues/18464
|
47
|
+
- https://bugs.ruby-lang.org/issues/19112
|
21
48
|
|
22
49
|
## Usage
|
23
50
|
|
@@ -0,0 +1,33 @@
|
|
1
|
+
exit 0 if !defined?(Ractor)
|
2
|
+
|
3
|
+
# This affects all tracepoints, including internal ones
|
4
|
+
|
5
|
+
def hello
|
6
|
+
"world"
|
7
|
+
end
|
8
|
+
|
9
|
+
traced_calls = 0
|
10
|
+
|
11
|
+
# Enable tracing
|
12
|
+
tracepoint = TracePoint.trace(:call) do |tp|
|
13
|
+
traced_calls += 1 if tp.callee_id == :hello
|
14
|
+
end
|
15
|
+
|
16
|
+
5.times { hello }
|
17
|
+
|
18
|
+
# Create a ractor and let it be garbage collected
|
19
|
+
r = Ractor.new { 10 }
|
20
|
+
r.take
|
21
|
+
r_id = r.object_id
|
22
|
+
r = nil
|
23
|
+
|
24
|
+
until (ObjectSpace._id2ref(r_id) rescue nil).nil?
|
25
|
+
GC.start
|
26
|
+
end
|
27
|
+
|
28
|
+
# Trigger extra calls to be traced, w/ Ractor enabled, they won't be.
|
29
|
+
5.times { hello }
|
30
|
+
|
31
|
+
tracepoint.disable
|
32
|
+
|
33
|
+
exit traced_calls == 10 ? 0 : 1
|
@@ -1,6 +1,84 @@
|
|
1
1
|
require "mkmf"
|
2
2
|
|
3
|
-
|
4
|
-
|
3
|
+
def abort_on_missing_ruby_header(name)
|
4
|
+
abort(
|
5
|
+
<<-MSG
|
6
|
+
|
7
|
+
PlainAPM extension needs #{name} Ruby library header to compile.
|
8
|
+
|
9
|
+
If Ruby is installed from a package on your system, please ensure the
|
10
|
+
corresponding Ruby development package is installed as well.
|
11
|
+
|
12
|
+
E.g. on Debian/Ubuntu, this would be achieved by running
|
13
|
+
|
14
|
+
sudo apt install ruby-dev
|
15
|
+
|
16
|
+
on CentOS/Fedora, run
|
17
|
+
|
18
|
+
sudo yum install ruby-devel
|
19
|
+
|
20
|
+
etc...
|
21
|
+
MSG
|
22
|
+
)
|
23
|
+
end
|
24
|
+
|
25
|
+
def warn_on_ruby_ractor_bugs
|
26
|
+
warn(
|
27
|
+
<<-MSG
|
28
|
+
|
29
|
+
PlainAPM extension to track object allocation on a per-thread basis is
|
30
|
+
built on top of Ruby's TracePoint API.
|
31
|
+
|
32
|
+
However, the currently running Ruby version contains bugs which,
|
33
|
+
when Tracepoints are used in together with Ractors, can cause
|
34
|
+
crashes or inconsistent tracing results.
|
35
|
+
|
36
|
+
Per-thread object allocation tracing will be disabled.
|
37
|
+
|
38
|
+
If you are sure your app is not using Ractors, you can override this by
|
39
|
+
installing plain_apm with --enable-object-tracing-override flag:
|
40
|
+
|
41
|
+
gem install plain_apm -- --enable-object-tracing-override
|
42
|
+
|
43
|
+
When using bundler, you can configure it to pass this flag to the gem
|
44
|
+
install by running:
|
45
|
+
|
46
|
+
bundle config set --global build.plain_apm --enable-object-tracing-override
|
47
|
+
|
48
|
+
See also:
|
49
|
+
|
50
|
+
https://bugs.ruby-lang.org/issues/18464
|
51
|
+
https://bugs.ruby-lang.org/issues/19112
|
52
|
+
|
53
|
+
MSG
|
54
|
+
)
|
55
|
+
end
|
56
|
+
|
57
|
+
def try_ruby(file)
|
58
|
+
system("ruby", "-W0", File.join(__dir__, file), [:out, :err] => File::NULL)
|
59
|
+
end
|
60
|
+
|
61
|
+
def enable_object_tracing
|
62
|
+
$defs.push("-DOBJECT_TRACING_ENABLED") unless $defs.include? "-DOBJECT_TRACING_ENABLED"
|
63
|
+
end
|
64
|
+
|
65
|
+
%w(
|
66
|
+
ruby/ruby.h
|
67
|
+
ruby/debug.h
|
68
|
+
).each do |header|
|
69
|
+
have_header(header) or abort_on_missing_ruby_header(header)
|
70
|
+
end
|
71
|
+
|
72
|
+
if enable_config("object-tracing-override", false)
|
73
|
+
enable_object_tracing
|
74
|
+
else
|
75
|
+
bugs = %w(bug18464.rb bug19112).count { |f| !try_ruby(f) }
|
76
|
+
|
77
|
+
if bugs.zero?
|
78
|
+
enable_object_tracing
|
79
|
+
else
|
80
|
+
warn_on_ruby_ractor_bugs
|
81
|
+
end
|
82
|
+
end
|
5
83
|
|
6
84
|
create_makefile("object_tracing")
|
@@ -1,25 +1,56 @@
|
|
1
1
|
#include <ruby/ruby.h>
|
2
2
|
#include <ruby/debug.h>
|
3
3
|
|
4
|
+
static VALUE rb_mPlainApm = Qnil;
|
5
|
+
static VALUE rb_mObjTracing = Qnil;
|
6
|
+
|
4
7
|
static __thread uint64_t allocated_objects = 0;
|
5
8
|
|
6
|
-
|
7
|
-
static
|
8
|
-
|
9
|
-
static VALUE total_thread_allocated_objects(VALUE self) {
|
10
|
-
return ULL2NUM(allocated_objects);
|
11
|
-
}
|
9
|
+
#ifdef OBJECT_TRACING_ENABLED
|
10
|
+
static int object_tracing_active = 0;
|
12
11
|
|
13
12
|
static void track_thread_allocated_objects(VALUE tpval, void *data) {
|
14
13
|
allocated_objects++;
|
15
14
|
}
|
15
|
+
#endif
|
16
|
+
|
17
|
+
static VALUE total_thread_allocated_objects(VALUE self) {
|
18
|
+
return ULL2NUM(allocated_objects);
|
19
|
+
}
|
16
20
|
|
17
21
|
void Init_object_tracing(void) {
|
18
22
|
rb_mPlainApm = rb_define_module("PlainApm");
|
23
|
+
rb_gc_register_address(&rb_mPlainApm);
|
24
|
+
|
19
25
|
rb_mObjTracing = rb_define_module_under(rb_mPlainApm, "ObjectTracing");
|
26
|
+
rb_gc_register_address(&rb_mObjTracing);
|
20
27
|
|
21
28
|
rb_define_singleton_method(rb_mObjTracing, "total_thread_allocated_objects", total_thread_allocated_objects, 0);
|
22
29
|
|
30
|
+
#ifdef OBJECT_TRACING_ENABLED
|
31
|
+
/* Ensure the tracepoint is attached only once. */
|
32
|
+
if (object_tracing_active) { return; }
|
33
|
+
|
34
|
+
object_tracing_active = 1;
|
35
|
+
|
36
|
+
/* Object allocation tracing is impacted by these bugs:
|
37
|
+
*
|
38
|
+
* https://bugs.ruby-lang.org/issues/19112 in Rubies 3.x.x
|
39
|
+
* https://bugs.ruby-lang.org/issues/18464 in Rubies 3.0, 3.1, and 3.2
|
40
|
+
*
|
41
|
+
* According to
|
42
|
+
*
|
43
|
+
* https://www.ruby-lang.org/en/downloads/branches/
|
44
|
+
*
|
45
|
+
* 3.0 goes out of maintenance mid 2024. The latter bug was backported to the
|
46
|
+
* other branches.
|
47
|
+
*
|
48
|
+
* For the former, there's https://github.com/ruby/ruby/pull/7184 open,
|
49
|
+
* unmerged as of Dec 2023.
|
50
|
+
*
|
51
|
+
*/
|
52
|
+
|
23
53
|
VALUE tpval = rb_tracepoint_new(0, RUBY_INTERNAL_EVENT_NEWOBJ, track_thread_allocated_objects, NULL);
|
24
54
|
rb_tracepoint_enable(tpval);
|
55
|
+
#endif
|
25
56
|
}
|
data/lib/plain_apm/version.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: plain_apm
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.8.
|
4
|
+
version: 0.8.4
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- PlainAPM Team
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2024-01-01 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: minitest
|
@@ -92,6 +92,8 @@ files:
|
|
92
92
|
- Gemfile
|
93
93
|
- LICENSE.txt
|
94
94
|
- README.md
|
95
|
+
- ext/object_tracing/bug18464.rb
|
96
|
+
- ext/object_tracing/bug19112.rb
|
95
97
|
- ext/object_tracing/extconf.rb
|
96
98
|
- ext/object_tracing/object_tracing.c
|
97
99
|
- lib/plain_apm.rb
|
@@ -130,7 +132,11 @@ metadata:
|
|
130
132
|
source_code_uri: https://github.com/plainapm/plainapm-ruby
|
131
133
|
changelog_uri: https://github.com/plainapm/plainapm-ruby/blob/main/CHANGELOG.md
|
132
134
|
github_repo: git@github.com:plainapm/plainapm-ruby.git
|
133
|
-
post_install_message:
|
135
|
+
post_install_message: "\n PlainAPM object tracing is affected by Ractor related
|
136
|
+
bugs,\n so it is not enabled by default on Ruby 3.\n\n If you are sure
|
137
|
+
your app does not use Ractors, this can be overridden by\n installing the gem
|
138
|
+
with --enable-object-tracing-override flag.\n\n Please see https://github.com/plainapm/plainapm-ruby/#installation
|
139
|
+
for\n more details.\n "
|
134
140
|
rdoc_options: []
|
135
141
|
require_paths:
|
136
142
|
- lib
|
@@ -138,7 +144,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
138
144
|
requirements:
|
139
145
|
- - ">="
|
140
146
|
- !ruby/object:Gem::Version
|
141
|
-
version: '2.
|
147
|
+
version: '2.7'
|
142
148
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
143
149
|
requirements:
|
144
150
|
- - ">="
|